Skip to content

Commit

Permalink
Reduce data returned by /ui/api/query endpoint
Browse files Browse the repository at this point in the history
  • Loading branch information
posulliv authored and findepi committed Oct 30, 2021
1 parent 6507f83 commit b37ebe8
Show file tree
Hide file tree
Showing 4 changed files with 200 additions and 13 deletions.
@@ -0,0 +1,187 @@
/*
* Licensed 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.
*/
package io.trino.server.ui;

import com.fasterxml.jackson.annotation.JsonProperty;
import io.trino.execution.QueryState;
import io.trino.server.BasicQueryInfo;
import io.trino.server.BasicQueryStats;
import io.trino.spi.ErrorCode;
import io.trino.spi.ErrorType;
import io.trino.spi.QueryId;
import io.trino.spi.memory.MemoryPoolId;
import io.trino.spi.resourcegroups.QueryType;
import io.trino.spi.resourcegroups.ResourceGroupId;

import javax.annotation.concurrent.Immutable;

import java.net.URI;
import java.util.Optional;

import static com.google.common.base.MoreObjects.toStringHelper;
import static java.util.Objects.requireNonNull;

@Immutable
public class TrimmedBasicQueryInfo
{
private static final int MAX_QUERY_PREVIEW_LENGTH = 300;

private final QueryId queryId;
private final String sessionUser;
private final Optional<String> sessionPrincipal;
private final Optional<String> sessionSource;
private final Optional<ResourceGroupId> resourceGroupId;
private final QueryState state;
private final MemoryPoolId memoryPool;
private final boolean scheduled;
private final URI self;
private final String queryTextPreview;
private final Optional<String> updateType;
private final Optional<String> preparedQuery;
private final BasicQueryStats queryStats;
private final Optional<ErrorType> errorType;
private final Optional<ErrorCode> errorCode;
private final Optional<QueryType> queryType;

public TrimmedBasicQueryInfo(BasicQueryInfo queryInfo)
{
this.queryId = requireNonNull(queryInfo.getQueryId(), "queryId is null");
this.sessionUser = requireNonNull(queryInfo.getSession().getUser(), "user is null");
this.sessionPrincipal = requireNonNull(queryInfo.getSession().getPrincipal(), "principal is null");
this.sessionSource = requireNonNull(queryInfo.getSession().getSource(), "source is null");
this.resourceGroupId = requireNonNull(queryInfo.getResourceGroupId(), "resourceGroupId is null");
this.state = requireNonNull(queryInfo.getState(), "state is null");
this.memoryPool = requireNonNull(queryInfo.getMemoryPool(), "memoryPool is null");
this.errorType = Optional.ofNullable(queryInfo.getErrorType());
this.errorCode = Optional.ofNullable(queryInfo.getErrorCode());
this.scheduled = queryInfo.isScheduled();
this.self = requireNonNull(queryInfo.getSelf(), "self is null");
String queryText = requireNonNull(queryInfo.getQuery(), "query is null");
if (queryText.length() <= MAX_QUERY_PREVIEW_LENGTH) {
this.queryTextPreview = queryText;
}
else {
this.queryTextPreview = queryText.substring(0, MAX_QUERY_PREVIEW_LENGTH - 1) + " ...";
}
this.updateType = requireNonNull(queryInfo.getUpdateType(), "updateType is null");
this.preparedQuery = requireNonNull(queryInfo.getPreparedQuery(), "preparedQuery is null");
this.queryStats = requireNonNull(queryInfo.getQueryStats(), "queryStats is null");
this.queryType = requireNonNull(queryInfo.getQueryType(), "queryType is null");
}

@JsonProperty
public QueryId getQueryId()
{
return queryId;
}

@JsonProperty
public String getSessionUser()
{
return sessionUser;
}

@JsonProperty
public Optional<String> getSessionPrincipal()
{
return sessionPrincipal;
}

@JsonProperty
public Optional<String> getSessionSource()
{
return sessionSource;
}

@JsonProperty
public Optional<ResourceGroupId> getResourceGroupId()
{
return resourceGroupId;
}

@JsonProperty
public QueryState getState()
{
return state;
}

@JsonProperty
public MemoryPoolId getMemoryPool()
{
return memoryPool;
}

@JsonProperty
public boolean isScheduled()
{
return scheduled;
}

@JsonProperty
public URI getSelf()
{
return self;
}

@JsonProperty
public String getQueryTextPreview()
{
return queryTextPreview;
}

@JsonProperty
public Optional<String> getUpdateType()
{
return updateType;
}

@JsonProperty
public Optional<String> getPreparedQuery()
{
return preparedQuery;
}

@JsonProperty
public BasicQueryStats getQueryStats()
{
return queryStats;
}

@JsonProperty
public Optional<ErrorType> getErrorType()
{
return errorType;
}

@JsonProperty
public Optional<ErrorCode> getErrorCode()
{
return errorCode;
}

@JsonProperty
public Optional<QueryType> getQueryType()
{
return queryType;
}

@Override
public String toString()
{
return toStringHelper(this)
.add("queryId", queryId)
.add("state", state)
.toString();
}
}
Expand Up @@ -71,17 +71,17 @@ public UiQueryResource(DispatchManager dispatchManager, AccessControl accessCont

@ResourceSecurity(WEB_UI)
@GET
public List<BasicQueryInfo> getAllQueryInfo(@QueryParam("state") String stateFilter, @Context HttpServletRequest servletRequest, @Context HttpHeaders httpHeaders)
public List<TrimmedBasicQueryInfo> getAllQueryInfo(@QueryParam("state") String stateFilter, @Context HttpServletRequest servletRequest, @Context HttpHeaders httpHeaders)
{
QueryState expectedState = stateFilter == null ? null : QueryState.valueOf(stateFilter.toUpperCase(Locale.ENGLISH));

List<BasicQueryInfo> queries = dispatchManager.getQueries();
queries = filterQueries(sessionContextFactory.extractAuthorizedIdentity(servletRequest, httpHeaders, alternateHeaderName), queries, accessControl);

ImmutableList.Builder<BasicQueryInfo> builder = new ImmutableList.Builder<>();
ImmutableList.Builder<TrimmedBasicQueryInfo> builder = new ImmutableList.Builder<>();
for (BasicQueryInfo queryInfo : queries) {
if (stateFilter == null || queryInfo.getState() == expectedState) {
builder.add(queryInfo);
builder.add(new TrimmedBasicQueryInfo(queryInfo));
}
}
return builder.build();
Expand Down
2 changes: 1 addition & 1 deletion core/trino-main/src/main/resources/webapp/dist/index.js

Large diffs are not rendered by default.

Expand Up @@ -67,7 +67,7 @@ export class QueryListItem extends React.Component {
}
}

return truncateString(formattedQueryText, 300);
return formattedQueryText;
}

render() {
Expand Down Expand Up @@ -122,10 +122,10 @@ export class QueryListItem extends React.Component {
</span>
</div>);

let user = (<span>{query.session.user}</span>);
if (query.session.principal) {
let user = (<span>{query.sessionUser}</span>);
if (query.sessionPrincipal) {
user = (
<span>{query.session.user}<span className="glyphicon glyphicon-lock-inverse" style={GLYPHICON_DEFAULT}/></span>
<span>{query.sessionUser}<span className="glyphicon glyphicon-lock-inverse" style={GLYPHICON_DEFAULT}/></span>
);
}

Expand Down Expand Up @@ -153,7 +153,7 @@ export class QueryListItem extends React.Component {
<div className="col-xs-12">
<span data-toggle="tooltip" data-placement="right" title="Source">
<span className="glyphicon glyphicon-log-in" style={GLYPHICON_DEFAULT}/>&nbsp;&nbsp;
<span>{truncateString(query.session.source, 35)}</span>
<span>{truncateString(query.sessionSource, 35)}</span>
</span>
</div>
</div>
Expand Down Expand Up @@ -188,7 +188,7 @@ export class QueryListItem extends React.Component {
</div>
<div className="row query-row-bottom">
<div className="col-xs-12">
<pre className="query-snippet"><code className="sql">{QueryListItem.stripQueryTextWhitespace(query.query)}</code></pre>
<pre className="query-snippet"><code className="sql">{QueryListItem.stripQueryTextWhitespace(query.queryTextPreview)}</code></pre>
</div>
</div>
</div>
Expand Down Expand Up @@ -302,15 +302,15 @@ export class QueryList extends React.Component {
const term = searchString.toLowerCase();
if (query.queryId.toLowerCase().indexOf(term) !== -1 ||
getHumanReadableState(query).toLowerCase().indexOf(term) !== -1 ||
query.query.toLowerCase().indexOf(term) !== -1) {
query.queryTextPreview.toLowerCase().indexOf(term) !== -1) {
return true;
}

if (query.session.user && query.session.user.toLowerCase().indexOf(term) !== -1) {
if (query.sessionUser && query.sessionUser.toLowerCase().indexOf(term) !== -1) {
return true;
}

if (query.session.source && query.session.source.toLowerCase().indexOf(term) !== -1) {
if (query.sessionSource && query.sessionSource.toLowerCase().indexOf(term) !== -1) {
return true;
}

Expand Down

0 comments on commit b37ebe8

Please sign in to comment.