- SOLR-58: make admin pages return XML and transform them to HTML using XSL

git-svn-id: https://svn.apache.org/repos/asf/incubator/solr/trunk@486373 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Otis Gospodnetic 2006-12-12 22:24:47 +00:00
parent 81bef1260c
commit 88b053e2cb
11 changed files with 659 additions and 333 deletions

View File

@ -118,6 +118,8 @@ Changes in runtime behavior
through multiple threads. Large commits also might be faster (klaas, SOLR-65) through multiple threads. Large commits also might be faster (klaas, SOLR-65)
9. Lazy field loading can be enabled via a solrconfig directive. This will be faster when 9. Lazy field loading can be enabled via a solrconfig directive. This will be faster when
not all stored fields are needed from a document (klaas, SOLR-52) not all stored fields are needed from a document (klaas, SOLR-52)
10. Made admin JSPs return XML and transform them with new XSL stylesheets
(Otis Gospodnetic, SOLR-58)
Optimizations Optimizations
1. getDocListAndSet can now generate both a DocList and a DocSet from a 1. getDocListAndSet can now generate both a DocList and a DocSet from a

View File

@ -1,20 +1,4 @@
<%@ page contentType="text/html; charset=utf-8" pageEncoding="UTF-8"%> <%@ page contentType="text/xml; charset=utf-8" pageEncoding="UTF-8" language="java" %>
<%--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
--%>
<%@ page import="org.apache.lucene.analysis.Analyzer, <%@ page import="org.apache.lucene.analysis.Analyzer,
org.apache.lucene.analysis.Token, org.apache.lucene.analysis.Token,
org.apache.lucene.analysis.TokenStream, org.apache.lucene.analysis.TokenStream,
@ -30,129 +14,86 @@
<%@ page import="java.io.StringReader"%> <%@ page import="java.io.StringReader"%>
<%@ page import="java.util.*"%> <%@ page import="java.util.*"%>
<%-- $Id$ --%> <?xml-stylesheet type="text/xsl" href="analysis.xsl"?>
<%-- $Source: /cvs/main/searching/org.apache.solrolarServer/resources/admin/analysis.jsp,v $ --%>
<%-- $Name: $ --%>
<%@include file="header.jsp" %> <%@include file="_info.jsp" %>
<% <%
String name = request.getParameter("name"); String name = request.getParameter("name");
if (name==null || name.length()==0) name=""; if (name == null || name.length() == 0) name = "";
String val = request.getParameter("val"); String val = request.getParameter("val");
if (val==null || val.length()==0) val=""; if (val == null || val.length() == 0) val = "";
String qval = request.getParameter("qval"); String qval = request.getParameter("qval");
if (qval==null || qval.length()==0) qval=""; if (qval == null || qval.length() == 0) qval = "";
String verboseS = request.getParameter("verbose"); String verboseS = request.getParameter("verbose");
boolean verbose = verboseS!=null && verboseS.equalsIgnoreCase("on"); boolean verbose = verboseS != null && verboseS.equalsIgnoreCase("on");
String qverboseS = request.getParameter("qverbose"); String qverboseS = request.getParameter("qverbose");
boolean qverbose = qverboseS!=null && qverboseS.equalsIgnoreCase("on"); boolean qverbose = qverboseS != null && qverboseS.equalsIgnoreCase("on");
String highlightS = request.getParameter("highlight"); String highlightS = request.getParameter("highlight");
boolean highlight = highlightS!=null && highlightS.equalsIgnoreCase("on"); boolean highlight = highlightS != null && highlightS.equalsIgnoreCase("on");
%> %>
<br clear="all"> <solr>
<%@include file="heading.jsp" %>
<h2>Field Analysis</h2> <analysis>
<form method="GET" action="analysis.jsp">
<table>
<tr>
<td>
<strong>Field name</strong>
</td>
<td>
<input class="std" name="name" type="text" value="<%= name %>">
</td>
</tr>
<tr>
<td>
<strong>Field value (Index)</strong>
<br/>
verbose output
<input name="verbose" type="checkbox"
<%= verbose ? "checked=\"true\"" : "" %> >
<br/>
highlight matches
<input name="highlight" type="checkbox"
<%= highlight ? "checked=\"true\"" : "" %> >
</td>
<td>
<textarea class="std" rows="3" cols="70" name="val"><%= val %></textarea>
</td>
</tr>
<tr>
<td>
<strong>Field value (Query)</strong>
<br/>
verbose output
<input name="qverbose" type="checkbox"
<%= qverbose ? "checked=\"true\"" : "" %> >
</td>
<td>
<textarea class="std" rows="1" cols="70" name="qval"><%= qval %></textarea>
</td>
</tr>
<tr>
<td>
</td>
<td>
<input class="stdbutton" type="submit" value="analyze">
</td>
</tr>
</table>
</form>
<% <%
SchemaField field=null; SchemaField field = null;
if (name!="") { if (name != "") {
try { try {
field = schema.getField(name); field = schema.getField(name);
} catch (Exception e) { } catch (Exception e) {
out.println("<strong>Unknown Field " + name + "</strong>"); out.println("<error>Unknown Field " + name + "</error>");
} }
} }
if (field!=null) { if (field != null) {
out.println(" <form>");
out.println(" <field>");
XML.escapeCharData(name, out);
out.println("</field>");
out.print(" <fieldIndexValue>");
XML.escapeCharData(val, out);
out.println(" </fieldIndexValue>");
out.print(" <fieldQueryValue>");
XML.escapeCharData(qval, out);
out.println(" </fieldQueryValue>");
out.println(" </form>");
HashSet<Tok> matches = null; HashSet<Tok> matches = null;
if (qval!="" && highlight) { if (qval != "" && highlight) {
Reader reader = new StringReader(qval); Reader reader = new StringReader(qval);
Analyzer analyzer = field.getType().getQueryAnalyzer(); Analyzer analyzer = field.getType().getQueryAnalyzer();
TokenStream tstream = analyzer.tokenStream(field.getName(),reader); TokenStream tstream = analyzer.tokenStream(field.getName(), reader);
List<Token> tokens = getTokens(tstream); List<Token> tokens = getTokens(tstream);
matches = new HashSet<Tok>(); matches = new HashSet<Tok>();
for (Token t : tokens) { matches.add( new Tok(t,0)); } for (Token t : tokens) { matches.add( new Tok(t, 0)); }
} }
if (val!="") { out.println(" <results>");
out.println("<h3>Index Analyzer</h3>"); if (val != "") {
doAnalyzer(out, field, val, false, verbose,matches); out.println("<indexAnalyzer>");
doAnalyzer(out, field, val, false, verbose, matches);
out.println("</indexAnalyzer>");
} }
if (qval!="") { if (qval != "") {
out.println("<h3>Query Analyzer</h3>"); out.println("<queryAnalyzer>");
doAnalyzer(out, field, qval, true, qverbose,null); doAnalyzer(out, field, qval, true, qverbose, null);
out.println("</queryAnalyzer>");
} }
out.println(" </results>");
} }
%> %>
</analysis>
</solr>
</body>
</html>
<%! <%!
private static void doAnalyzer(JspWriter out, SchemaField field, String val, boolean queryAnalyser, boolean verbose, Set<Tok> match) throws Exception { private static void doAnalyzer(JspWriter out, SchemaField field, String val, boolean queryAnalyser, boolean verbose, Set<Tok> match) throws Exception {
Reader reader = new StringReader(val); Reader reader = new StringReader(val);
FieldType ft = field.getType(); FieldType ft = field.getType();
Analyzer analyzer = queryAnalyser ? Analyzer analyzer = queryAnalyser ? ft.getQueryAnalyzer() : ft.getAnalyzer();
ft.getQueryAnalyzer() : ft.getAnalyzer();
if (analyzer instanceof TokenizerChain) { if (analyzer instanceof TokenizerChain) {
TokenizerChain tchain = (TokenizerChain)analyzer; TokenizerChain tchain = (TokenizerChain)analyzer;
TokenizerFactory tfac = tchain.getTokenizerFactory(); TokenizerFactory tfac = tchain.getTokenizerFactory();
@ -161,12 +102,14 @@
TokenStream tstream = tfac.create(reader); TokenStream tstream = tfac.create(reader);
List<Token> tokens = getTokens(tstream); List<Token> tokens = getTokens(tstream);
tstream = tfac.create(reader); tstream = tfac.create(reader);
// write tokenizer factories
if (verbose) { if (verbose) {
writeHeader(out, tfac.getClass(), tfac.getArgs()); writeHeader(out, tfac.getClass(), tfac.getArgs());
} }
writeTokens(out, tokens, ft, verbose, match); writeTokens(out, tokens, ft, verbose, match);
// write filter factories
for (TokenFilterFactory filtfac : filtfacs) { for (TokenFilterFactory filtfac : filtfacs) {
if (verbose) { if (verbose) {
writeHeader(out, filtfac.getClass(), filtfac.getArgs()); writeHeader(out, filtfac.getClass(), filtfac.getArgs());
@ -183,7 +126,6 @@
writeTokens(out, tokens, ft, verbose, match); writeTokens(out, tokens, ft, verbose, match);
} }
} else { } else {
TokenStream tstream = analyzer.tokenStream(field.getName(),reader); TokenStream tstream = analyzer.tokenStream(field.getName(),reader);
List<Token> tokens = getTokens(tstream); List<Token> tokens = getTokens(tstream);
@ -199,7 +141,7 @@
List<Token> tokens = new ArrayList<Token>(); List<Token> tokens = new ArrayList<Token>();
while (true) { while (true) {
Token t = tstream.next(); Token t = tstream.next();
if (t==null) break; if (t == null) break;
tokens.add(t); tokens.add(t);
} }
return tokens; return tokens;
@ -210,8 +152,8 @@
Token token; Token token;
int pos; int pos;
Tok(Token token, int pos) { Tok(Token token, int pos) {
this.token=token; this.token = token;
this.pos=pos; this.pos = pos;
} }
public boolean equals(Object o) { public boolean equals(Object o) {
@ -221,7 +163,7 @@
return token.termText().hashCode(); return token.termText().hashCode();
} }
public String toString() { public String toString() {
return token.termText(); return token.termText() + " at position " + pos;
} }
} }
@ -229,81 +171,38 @@
public String toStr(Object o); public String toStr(Object o);
} }
private static void printRow(JspWriter out, String header, List[] arrLst, ToStr converter, boolean multival, boolean verbose, Set<Tok> match) throws IOException {
// find the maximum number of terms for any position
int maxSz=1;
if (multival) {
for (List lst : arrLst) {
maxSz = Math.max(lst.size(), maxSz);
}
}
for (int idx=0; idx<maxSz; idx++) {
out.println("<tr>");
if (idx==0 && verbose) {
if (header != null) {
out.print("<th NOWRAP rowspan=\""+maxSz+"\">");
XML.escapeCharData(header,out);
out.println("</th>");
}
}
for (List<Tok> lst : arrLst) {
if (lst.size() <= idx) continue;
if (match!=null && match.contains(lst.get(idx))) {
out.print("<td class=\"highlight\"");
} else {
out.print("<td class=\"debugdata\"");
}
if (idx==0 && lst.size()==1 && maxSz > 1) {
out.print("rowspan=\""+maxSz+'"');
}
out.print('>');
XML.escapeCharData(converter.toStr(lst.get(idx)), out);
out.print("</td>");
}
out.println("</tr>");
}
}
static void writeHeader(JspWriter out, Class clazz, Map<String,String> args) throws IOException { static void writeHeader(JspWriter out, Class clazz, Map<String,String> args) throws IOException {
out.print("<h4>"); out.println(" <factory class=\"" + clazz.getName() + "\">");
out.print(clazz.getName()); out.println(" <args>");
XML.escapeCharData(" "+args,out); for (Iterator<String> iter = args.keySet().iterator(); iter.hasNext(); ) {
out.println("</h4>"); String key = iter.next();
String value = args.get(key);
out.println(" <arg name=\"" + key + "\">" + value + "</arg>");
}
out.println(" </args>");
} }
// readable, raw, pos, type, start/end // readable, raw, pos, type, start/end
static void writeTokens(JspWriter out, List<Token> tokens, final FieldType ft, boolean verbose, Set<Tok> match) throws IOException { static void writeTokens(JspWriter out, List<Token> tokens, final FieldType ft, boolean verbose, Set<Tok> match) throws IOException {
// Use a map to tell what tokens are in what positions // Use a map to tell what tokens are in what positions
// because some tokenizers/filters may do funky stuff with // because some tokenizers/filters may do funky stuff with
// very large increments, or negative increments. // very large increments, or negative increments.
HashMap<Integer,List<Tok>> map = new HashMap<Integer,List<Tok>>(); HashMap<Integer, List<Tok>> map = new HashMap<Integer, List<Tok>>();
boolean needRaw=false; boolean needRaw = false;
int pos=0; int pos = 0;
for (Token t : tokens) { for (Token t : tokens) {
if (!t.termText().equals(ft.indexedToReadable(t.termText()))) { if (!t.termText().equals(ft.indexedToReadable(t.termText()))) {
needRaw=true; needRaw = true;
} }
pos += t.getPositionIncrement(); pos += t.getPositionIncrement();
List lst = map.get(pos); List lst = map.get(pos);
if (lst==null) { if (lst == null) {
lst = new ArrayList(1); lst = new ArrayList(1);
map.put(pos,lst); map.put(pos, lst);
} }
Tok tok = new Tok(t,pos); Tok tok = new Tok(t, pos);
lst.add(tok); lst.add(tok);
} }
@ -330,70 +229,21 @@
); );
out.println("<table width=\"auto\" class=\"analysis\" border=\"1\">"); out.println(" <tokens>");
for (int i = 0; i < arr.length; i++) {
if (verbose) { for (Tok tok : arr[i]) {
printRow(out,"term position", arr, new ToStr() { out.print(" <token");
public String toStr(Object o) { out.print(" type=\"" + tok.token.type() + "\"");
return Integer.toString(((Tok)o).pos); out.print(" pos=\"" + tok.pos + "\"");
} out.print(" start=\"" + tok.token.startOffset() + "\"");
} out.print(" end=\"" + tok.token.endOffset() + "\"");
,false out.print(">");
,verbose out.print(tok.token.termText());
,null); out.println(" </token>");
} }
}
out.println(" </tokens>");
printRow(out,"term text", arr, new ToStr() { out.println(" </factory>");
public String toStr(Object o) {
return ft.indexedToReadable( ((Tok)o).token.termText() );
}
}
,true
,verbose
,match
);
if (needRaw) {
printRow(out,"raw text", arr, new ToStr() {
public String toStr(Object o) {
// todo: output in hex or something?
// check if it's all ascii or not?
return ((Tok)o).token.termText();
}
}
,true
,verbose
,match
);
}
if (verbose) {
printRow(out,"term type", arr, new ToStr() {
public String toStr(Object o) {
return ((Tok)o).token.type();
}
}
,true
,verbose,
null
);
}
if (verbose) {
printRow(out,"source start,end", arr, new ToStr() {
public String toStr(Object o) {
Token t = ((Tok)o).token;
return Integer.toString(t.startOffset()) + ',' + t.endOffset() ;
}
}
,true
,verbose
,null
);
}
out.println("</table>");
} }
%> %>

View File

@ -0,0 +1,177 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- $Id$ -->
<!-- $URL$ -->
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output
method="html"
indent="yes"
doctype-public="-//W3C//DTD HTML 4.01//EN"
doctype-system="http://www.w3.org/TR/html4/strict.dtd" />
<xsl:template match="/">
<html>
<head>
<link rel="stylesheet" type="text/css" href="solr-admin.css"></link>
<link rel="icon" href="/favicon.ico" type="image/ico"></link>
<link rel="shortcut icon" href="/favicon.ico" type="image/ico"></link>
<title>SOLR Info</title>
</head>
<body>
<a href="">
<img border="0" align="right" height="61" width="142" src="solr-head.gif" alt="SOLR"/>
</a>
<h1>Solr Admin (<xsl:value-of select="solr/meta/collection" />)</h1>
<div style="margin-top: 1em;">
<h2>Field Analysis</h2>
<xsl:apply-templates/>
<a href=".">Return to Admin Page</a>
</div>
</body>
</html>
</xsl:template>
<xsl:include href="meta.xsl"/>
<xsl:template match="solr/analysis/form">
<form method="GET" action="analysis.jsp">
<table>
<tr>
<td>
<strong>Field name</strong>
</td>
<td>
<input class="std" name="name" type="text" value="{field}"/>
</td>
</tr>
<tr>
<td>
<strong>Field value (Index)</strong>
<br/>
verbose output <input name="verbose" type="checkbox" checked="true"/>
<br/>
highlight matches <input name="highlight" type="checkbox" checked="true"/>
</td>
<td>
<textarea class="std" rows="3" cols="70" name="val"><xsl:value-of select="fieldIndexValue" /></textarea>
</td>
</tr>
<tr>
<td>
<strong>Field value (Query)</strong>
<br/>
verbose output <input name="qverbose" type="checkbox" checked="true"/>
</td>
<td>
<textarea class="std" rows="1" cols="70" name="qval"><xsl:value-of select="fieldQueryValue" /></textarea>
</td>
</tr>
<tr>
<td>
</td>
<td>
<input class="stdbutton" type="submit" value="analyze"/>
</td>
</tr>
</table>
</form>
</xsl:template>
<xsl:template match="solr/analysis/results/indexAnalyzer">
<h4>Index Analyzer</h4>
<xsl:for-each select="factory">
<h5 style="margin-left: 1em;"><xsl:apply-templates select="@class"/></h5>
<xsl:apply-templates/>
</xsl:for-each>
</xsl:template>
<xsl:template match="solr/analysis/results/indexAnalyzer/factory/args">
<div style="margin-left: 2em; font-weight: bold;">{
<xsl:for-each select="arg">
<xsl:apply-templates select="@name"/>=<xsl:value-of select="."/>,
</xsl:for-each>
}</div>
</xsl:template>
<xsl:template match="solr/analysis/results/indexAnalyzer/factory/tokens">
<div style="margin-left: 2em;">
<table width="auto" class="analysis" border="1">
<tr>
<th>text</th>
<th>type</th>
<th>position</th>
<th>start</th>
<th>end</th>
</tr>
<xsl:for-each select="token">
<tr>
<td><xsl:value-of select="."/></td>
<td><xsl:apply-templates select="@type"/></td>
<td><xsl:apply-templates select="@pos"/></td>
<td><xsl:apply-templates select="@start"/></td>
<td><xsl:apply-templates select="@end"/></td>
</tr>
</xsl:for-each>
</table>
</div>
</xsl:template>
<xsl:template match="solr/analysis/results/queryAnalyzer">
<h4>Query Analyzer</h4>
<xsl:for-each select="factory">
<h5 style="margin-left: 1em;"><xsl:apply-templates select="@class"/></h5>
<xsl:apply-templates/>
</xsl:for-each>
</xsl:template>
<xsl:template match="solr/analysis/results/queryAnalyzer/factory/args">
<div style="margin-left: 2em; font-weight: bold;">{
<xsl:for-each select="arg">
<xsl:apply-templates select="@name"/>=<xsl:value-of select="."/>,
</xsl:for-each>
}</div>
</xsl:template>
<xsl:template match="solr/analysis/results/queryAnalyzer/factory/tokens">
<div style="margin-left: 2em;">
<table width="auto" class="analysis" border="1">
<tr>
<th>text</th>
<th>type</th>
<th>position</th>
<th>start</th>
<th>end</th>
</tr>
<xsl:for-each select="token">
<tr>
<td><xsl:value-of select="."/></td>
<td><xsl:apply-templates select="@type"/></td>
<td><xsl:apply-templates select="@pos"/></td>
<td><xsl:apply-templates select="@start"/></td>
<td><xsl:apply-templates select="@end"/></td>
</tr>
</xsl:for-each>
</table>
</div>
</xsl:template>
</xsl:stylesheet>

View File

@ -0,0 +1,23 @@
<%--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
--%>
<meta>
<collection><%= collectionName %></collection>
<host><%= hostname %></host>
<port><%= port %></port>
<cwd><%= cwd %></cwd>
<solrHome><%= solrHome %></solrHome>
</meta>

View File

@ -1,4 +1,4 @@
<%@ page contentType="text/html; charset=utf-8" pageEncoding="UTF-8"%> <%@ page contentType="text/xml; charset=utf-8" pageEncoding="UTF-8" language="java" %>
<%-- <%--
Licensed to the Apache Software Foundation (ASF) under one or more Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with contributor license agreements. See the NOTICE file distributed with
@ -24,12 +24,11 @@
<%@ page import="java.util.logging.Level"%> <%@ page import="java.util.logging.Level"%>
<%@ page import="java.util.logging.LogManager"%> <%@ page import="java.util.logging.LogManager"%>
<%@ page import="java.util.logging.Logger"%> <%@ page import="java.util.logging.Logger"%>
<%@include file="header.jsp" %>
<?xml-stylesheet type="text/xsl" href="logging.xsl"?>
<% <%
LogManager mgr = LogManager.getLogManager();
Logger log = SolrCore.log; Logger log = SolrCore.log;
Logger parent = log.getParent(); Logger parent = log.getParent();
while(parent != null) { while(parent != null) {
log = parent; log = parent;
@ -38,39 +37,12 @@
Level lvl = log.getLevel(); Level lvl = log.getLevel();
%> %>
<br clear="all"> <solr>
<h2>Solr Logging</h2> <logging>
<table> <% if (lvl != null) {%>
<tr> <logLevel><%= lvl.toString() %></logLevel>
<td>
<H3>Log Level:</H3>
</td>
<td>
<% if (lvl!=null) {%>
<%= lvl.toString() %><br>
<% } else { %> <% } else { %>
null<br> <logLevel>null</logLevel>
<% } %> <% } %>
</td> </logging>
</tr> </solr>
<tr>
<td>
Set Level
</td>
<td>
[<a href=action.jsp?log=ALL>ALL</a>]
[<a href=action.jsp?log=CONFIG>CONFIG</a>]
[<a href=action.jsp?log=FINE>FINE</a>]
[<a href=action.jsp?log=FINER>FINER</a>]
[<a href=action.jsp?log=FINEST>FINEST</a>]
[<a href=action.jsp?log=INFO>INFO</a>]
[<a href=action.jsp?log=OFF>OFF</a>]
[<a href=action.jsp?log=SEVERE>SEVERE</a>]
[<a href=action.jsp?log=WARNING>WARNING</a>]
</td>
</tr>
</table>
<br><br>
<a href=".">Return to Admin Page</a>
</body>
</html>

View File

@ -0,0 +1,89 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- $Id$ -->
<!-- $URL$ -->
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output
method="html"
indent="yes"
doctype-public="-//W3C//DTD HTML 4.01//EN"
doctype-system="http://www.w3.org/TR/html4/strict.dtd" />
<xsl:template match="/">
<html>
<head>
<link rel="stylesheet" type="text/css" href="solr-admin.css"></link>
<link rel="icon" href="/favicon.ico" type="image/ico"></link>
<link rel="shortcut icon" href="/favicon.ico" type="image/ico"></link>
<title>Solr Admin: Logging</title>
</head>
<body>
<a href="">
<img border="0" align="right" height="61" width="142" src="solr-head.gif" alt="SOLR">
</img>
</a>
<h1>Solr Admin (<xsl:value-of select="solr/meta/collection" />)</h1>
<div style="margin-top: 1em;">
<xsl:apply-templates/>
<div>
</div>
<a href=".">Return to Admin Page</a>
</div>
</body>
</html>
</xsl:template>
<xsl:include href="meta.xsl"/>
<xsl:template match="solr/logging">
<br clear="all"/>
<h2>Solr Logging</h2>
<table>
<tr>
<td>
<H3>Log Level:</H3>
</td>
<td>
<xsl:value-of select="logLevel" />
</td>
</tr>
<tr>
<td>
Set Level
</td>
<td>
[<a href="action.jsp?log=ALL">ALL</a>]
[<a href="action.jsp?log=CONFIG">CONFIG</a>]
[<a href="action.jsp?log=FINE">FINE</a>]
[<a href="action.jsp?log=FINER">FINER</a>]
[<a href="action.jsp?log=FINEST">FINEST</a>]
[<a href="action.jsp?log=INFO">INFO</a>]
[<a href="action.jsp?log=OFF">OFF</a>]
[<a href="action.jsp?log=SEVERE">SEVERE</a>]
[<a href="action.jsp?log=WARNING">WARNING</a>]
</td>
</tr>
</table>
</xsl:template>
</xsl:stylesheet>

View File

@ -0,0 +1,32 @@
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output
method="html"
indent="yes"
doctype-public="-//W3C//DTD HTML 4.01//EN"
doctype-system="http://www.w3.org/TR/html4/strict.dtd" />
<xsl:template match="solr/meta">
<xsl:value-of select="host" />:<xsl:value-of select="port" />
cwd=<xsl:value-of select="cwd" /> SolrHome=<xsl:value-of select="solrHome" />
</xsl:template>
</xsl:stylesheet>

View File

@ -1,4 +1,4 @@
<%@ page contentType="text/html; charset=utf-8" pageEncoding="UTF-8"%> <%@ page contentType="text/xml; charset=utf-8" pageEncoding="UTF-8" language="java" %>
<%-- <%--
Licensed to the Apache Software Foundation (ASF) under one or more Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with contributor license agreements. See the NOTICE file distributed with
@ -17,10 +17,16 @@
--%> --%>
<%@ page import="org.apache.solr.core.SolrConfig, <%@ page import="org.apache.solr.core.SolrConfig,
org.apache.solr.core.SolrCore, org.apache.solr.core.SolrCore,
org.apache.solr.util.XML,
org.apache.solr.core.SolrException"%> org.apache.solr.core.SolrException"%>
<%@ page import="org.apache.solr.request.LocalSolrQueryRequest"%> <%@ page import="org.apache.solr.request.LocalSolrQueryRequest"%>
<%@ page import="org.apache.solr.request.SolrQueryResponse"%> <%@ page import="org.apache.solr.request.SolrQueryResponse"%>
<%@ page import="java.util.StringTokenizer"%> <%@ page import="java.util.StringTokenizer"%>
<?xml-stylesheet type="text/xsl" href="ping.xsl"?>
<solr>
<ping>
<% <%
SolrCore core = SolrCore.getSolrCore(); SolrCore core = SolrCore.getSolrCore();
@ -40,12 +46,31 @@
SolrQueryResponse resp = new SolrQueryResponse(); SolrQueryResponse resp = new SolrQueryResponse();
try { try {
core.execute(req,resp); core.execute(req,resp);
if (resp.getException() != null) { if (resp.getException() == null) {
response.sendError(500, SolrException.toStr(resp.getException())); // No need for explicit status in the body, when the standard HTTP
// response codes already transmit success/failure message
// out.println("<status>200</status>");
}
else if (resp.getException() != null) {
// No need for explicit status in the body, when the standard HTTP
// response codes already transmit success/failure message
// out.println("<status>500</status>");
out.println("<error>");
XML.escapeCharData(SolrException.toStr(resp.getException()), out);
out.println("</error>");
response.sendError(500);
} }
} catch (Throwable t) { } catch (Throwable t) {
response.sendError(500, SolrException.toStr(t)); // No need for explicit status in the body, when the standard HTTP
// response codes already transmit success/failure message
// out.println("<status>500</status>");
out.println("<error>");
XML.escapeCharData(SolrException.toStr(t), out);
out.println("</error>");
response.sendError(500);
} finally { } finally {
req.close(); req.close();
} }
%> %>
</ping>
</solr>

View File

@ -0,0 +1,69 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- $Id$ -->
<!-- $URL$ -->
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output
method="html"
indent="yes"
doctype-public="-//W3C//DTD HTML 4.01//EN"
doctype-system="http://www.w3.org/TR/html4/strict.dtd" />
<xsl:template match="/">
<html>
<head>
<link rel="stylesheet" type="text/css" href="solr-admin.css"></link>
<link rel="icon" href="/favicon.ico" type="image/ico"></link>
<link rel="shortcut icon" href="/favicon.ico" type="image/ico"></link>
<title>Solr Admin: Ping</title>
</head>
<body>
<a href="">
<img border="0" align="right" height="61" width="142" src="solr-head.gif" alt="SOLR">
</img>
</a>
<h1>Solr Admin (<xsl:value-of select="solr/meta/collection" />)</h1>
<div style="margin-top: 1em;">
<xsl:apply-templates/>
<div>
</div>
<a href=".">Return to Admin Page</a>
</div>
</body>
</html>
</xsl:template>
<xsl:include href="meta.xsl"/>
<xsl:template match="solr/ping">
<table>
<tr>
<td>
<H3>Ping</H3>
</td>
<td>
<xsl:value-of select="error" />
</td>
</tr>
</table>
</xsl:template>
</xsl:stylesheet>

View File

@ -1,4 +1,4 @@
<%@ page contentType="text/html; charset=utf-8" pageEncoding="UTF-8"%> <%@ page contentType="text/xml; charset=utf-8" pageEncoding="UTF-8" language="java" %>
<%-- <%--
Licensed to the Apache Software Foundation (ASF) under one or more Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with contributor license agreements. See the NOTICE file distributed with
@ -18,101 +18,87 @@
<%@ page import="java.lang.management.ManagementFactory, <%@ page import="java.lang.management.ManagementFactory,
java.lang.management.ThreadMXBean, java.lang.management.ThreadMXBean,
java.lang.management.ThreadInfo, java.lang.management.ThreadInfo,
java.io.IOException"%> java.io.IOException,
<%@include file="header.jsp" %> org.apache.solr.util.XML"%>
<?xml-stylesheet type="text/xsl" href="threaddump.xsl"?>
<%! <%!
static ThreadMXBean tmbean = ManagementFactory.getThreadMXBean(); static ThreadMXBean tmbean = ManagementFactory.getThreadMXBean();
%> %>
<br clear="all"> <solr>
<h2>Thread Dump</h2> <system>
<table> <jvm>
<tr> <version><%=System.getProperty("java.vm.version")%></version>
<td> <name><%=System.getProperty("java.vm.name")%></name>
<% </jvm>
out.print(System.getProperty("java.vm.name") + <threadCount>
" " + System.getProperty("java.vm.version") + "<br>"); <current><%=tmbean.getThreadCount()%></current>
%> <peak><%=tmbean.getPeakThreadCount()%></peak>
</td> <daemon><%=tmbean.getDaemonThreadCount()%></daemon>
</tr> </threadCount>
<tr>
<td>
<% <%
long[] tids; long[] tids;
ThreadInfo[] tinfos; ThreadInfo[] tinfos;
out.print("Thread Count: current=" + tmbean.getThreadCount() +
" deamon=" + tmbean.getDaemonThreadCount() +
" peak=" + tmbean.getPeakThreadCount());
%>
</td>
</tr>
<tr>
<td>
<%
tids = tmbean.findMonitorDeadlockedThreads(); tids = tmbean.findMonitorDeadlockedThreads();
if (tids == null) { if (tids != null) {
out.print("No deadlock found."); out.println(" <deadlocks>");
}
else {
out.print("Deadlock found :-");
tinfos = tmbean.getThreadInfo(tids, Integer.MAX_VALUE); tinfos = tmbean.getThreadInfo(tids, Integer.MAX_VALUE);
for (ThreadInfo ti : tinfos) { for (ThreadInfo ti : tinfos) {
printThreadInfo(ti, out); printThreadInfo(ti, out);
} }
out.println(" </deadlocks>");
} }
%> %>
</td>
</tr>
<tr>
<td>
<% <%
out.print("Full Thread Dump:<br>");
tids = tmbean.getAllThreadIds(); tids = tmbean.getAllThreadIds();
tinfos = tmbean.getThreadInfo(tids, Integer.MAX_VALUE); tinfos = tmbean.getThreadInfo(tids, Integer.MAX_VALUE);
out.println(" <threadDump>");
for (ThreadInfo ti : tinfos) { for (ThreadInfo ti : tinfos) {
printThreadInfo(ti, out); printThreadInfo(ti, out);
} }
out.println(" </threadDump>");
%> %>
</td> </system>
</tr> </solr>
</table>
<br><br>
<a href=".">Return to Admin Page</a>
</body>
</html>
<%! <%!
static String INDENT = "&nbsp&nbsp&nbsp&nbsp ";
static void printThreadInfo(ThreadInfo ti, JspWriter out) throws IOException { static void printThreadInfo(ThreadInfo ti, JspWriter out) throws IOException {
long tid = ti.getThreadId(); long tid = ti.getThreadId();
StringBuilder sb = new StringBuilder("\"" + ti.getThreadName() + "\"" + out.println(" <thread>");
" Id=" + tid + out.println(" <id>" + tid + "</id>");
" in " + ti.getThreadState()); out.print(" <name>");
XML.escapeCharData(ti.getThreadName(), out);
out.println("</name>");
out.println(" <state>" + ti.getThreadState() + "</state>");
if (ti.getLockName() != null) { if (ti.getLockName() != null) {
sb.append(" on lock=" + ti.getLockName()); out.println(" <lock>" + ti.getLockName() + "</lock>");
} }
if (ti.isSuspended()) { if (ti.isSuspended()) {
sb.append(" (suspended)"); out.println(" <suspended/>");
} }
if (ti.isInNative()) { if (ti.isInNative()) {
sb.append(" (running in native)"); out.println(" <inNative/>");
} }
if (tmbean.isThreadCpuTimeSupported()) { if (tmbean.isThreadCpuTimeSupported()) {
sb.append(" total cpu time=" out.println(" <cpuTime>" + formatNanos(tmbean.getThreadCpuTime(tid)) + "</cpuTime>");
+formatNanos(tmbean.getThreadCpuTime(tid))); out.println(" <userTime>" + formatNanos(tmbean.getThreadUserTime(tid)) + "</userTime>");
sb.append(" user time="
+formatNanos(tmbean.getThreadUserTime(tid)));
} }
out.print(sb.toString()+"<br>");
if (ti.getLockOwnerName() != null) { if (ti.getLockOwnerName() != null) {
out.print(INDENT + " owned by " + ti.getLockOwnerName() + out.println(" <owner>");
" Id=" + ti.getLockOwnerId()+"<br>"); out.println(" <name>" + ti.getLockOwnerName() + "</name>");
out.println(" <id>" + ti.getLockOwnerId() + "</id>");
out.println(" </owner>");
} }
out.println(" <stackTrace>");
for (StackTraceElement ste : ti.getStackTrace()) { for (StackTraceElement ste : ti.getStackTrace()) {
out.print(INDENT + "at " + ste.toString()+"<br>"); out.print(" <line>");
XML.escapeCharData("at " + ste.toString(), out);
out.println(" </line>");
} }
out.print("<br>"); out.println(" </stackTrace>");
out.println(" </thread>");
} }
static String formatNanos(long ns) { static String formatNanos(long ns) {

View File

@ -0,0 +1,101 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- $Id$ -->
<!-- $URL$ -->
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output
method="html"
indent="yes"
doctype-public="-//W3C//DTD HTML 4.01//EN"
doctype-system="http://www.w3.org/TR/html4/strict.dtd" />
<xsl:template match="/">
<html>
<head>
<link rel="stylesheet" type="text/css" href="solr-admin.css"></link>
<link rel="icon" href="/favicon.ico" type="image/ico"></link>
<link rel="shortcut icon" href="/favicon.ico" type="image/ico"></link>
<title>SOLR Info</title>
</head>
<body>
<a href="">
<img border="0" align="right" height="61" width="142" src="solr-head.gif" alt="SOLR"/>
</a>
<h1>Solr Admin (<xsl:value-of select="solr/meta/collection" />)</h1>
<h2>Thread Dump</h2>
<div style="margin-top: 1em;">
<table>
<xsl:apply-templates/>
</table>
<a href=".">Return to Admin Page</a>
</div>
</body>
</html>
</xsl:template>
<xsl:include href="meta.xsl"/>
<xsl:template match="solr/system/jvm">
<tr>
<td><xsl:value-of select="name"/> <xsl:value-of select="version"/></td>
</tr>
</xsl:template>
<xsl:template match="solr/system/threadCount">
<tr>
<td>
Thread Count:
current=<xsl:value-of select="current"/>,
peak=<xsl:value-of select="peak"/>,
daemon=<xsl:value-of select="daemon"/></td>
</tr>
</xsl:template>
<xsl:template match="solr/system/threadDump">
<div>Full Thread Dump:</div>
<xsl:for-each select="thread">
<!-- OG: TODO: add suspended/native conditionals -->
<tr>
<td style="margin-left: 1em; font-weight: bold;">
'<xsl:value-of select="name"/>'
Id=<xsl:value-of select="id"/>,
<xsl:value-of select="state"/>
on lock=<xsl:value-of select="lock"/>,
total cpu time=<xsl:value-of select="cpuTime"/>
user time=<xsl:value-of select="userTime"/>
</td>
</tr>
<xsl:apply-templates select="stackTrace"/>
</xsl:for-each>
</xsl:template>
<xsl:template match="stackTrace">
<tr>
<td style="margin-left: 1em;">
<xsl:for-each select="line">
<xsl:value-of select="."/><br/>
</xsl:for-each>
</td>
</tr>
</xsl:template>
</xsl:stylesheet>