MetadataResource: Fix handling of includeDisabled. (#3042)

This commit is contained in:
Gian Merlino 2016-06-01 11:56:37 -07:00 committed by Fangjin Yang
parent 5e44ed7132
commit 874a0a4bdd
1 changed files with 60 additions and 82 deletions

View File

@ -22,8 +22,9 @@ package io.druid.server.http;
import com.google.common.base.Function;
import com.google.common.base.Predicate;
import com.google.common.collect.Collections2;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import com.google.common.collect.Sets;
import com.google.inject.Inject;
import com.metamx.common.Pair;
import com.sun.jersey.spi.container.ResourceFilters;
@ -51,11 +52,10 @@ import javax.ws.rs.core.Context;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import java.io.IOException;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
/**
*/
@ -82,22 +82,39 @@ public class MetadataResource
@Path("/datasources")
@Produces(MediaType.APPLICATION_JSON)
public Response getDatabaseDataSources(
@QueryParam("full") String full,
@QueryParam("includeDisabled") String includeDisabled,
@QueryParam("full") final String full,
@QueryParam("includeDisabled") final String includeDisabled,
@Context final HttpServletRequest req
)
{
Response.ResponseBuilder builder = Response.status(Response.Status.OK);
final Set<String> dataSourceNamesPreAuth;
if (includeDisabled != null) {
dataSourceNamesPreAuth = Sets.newTreeSet(metadataSegmentManager.getAllDatasourceNames());
} else {
dataSourceNamesPreAuth = Sets.newTreeSet(
Iterables.transform(
metadataSegmentManager.getInventory(),
new Function<DruidDataSource, String>()
{
@Override
public String apply(DruidDataSource input)
{
return input.getName();
}
}
)
);
}
final Set<String> dataSourceNamesPostAuth;
final Collection<DruidDataSource> druidDataSources;
if (authConfig.isEnabled()) {
// This is an experimental feature, see - https://github.com/druid-io/druid/pull/2424
final Map<Pair<Resource, Action>, Access> resourceAccessMap = new HashMap<>();
final AuthorizationInfo authorizationInfo = (AuthorizationInfo) req.getAttribute(AuthConfig.DRUID_AUTH_TOKEN);
if (includeDisabled != null) {
return builder.entity(
Collections2.filter(
metadataSegmentManager.getAllDatasourceNames(),
dataSourceNamesPostAuth = ImmutableSet.copyOf(
Sets.filter(
dataSourceNamesPreAuth,
new Predicate<String>()
{
@Override
@ -115,9 +132,16 @@ public class MetadataResource
}
}
}
)).build();
)
);
} else {
druidDataSources =
dataSourceNamesPostAuth = dataSourceNamesPreAuth;
}
// Cannot do both includeDisabled and full, let includeDisabled take priority
// Always use dataSourceNamesPostAuth to determine the set of returned dataSources
if (full != null && includeDisabled == null) {
return Response.ok().entity(
Collections2.filter(
metadataSegmentManager.getInventory(),
new Predicate<DruidDataSource>()
@ -125,60 +149,14 @@ public class MetadataResource
@Override
public boolean apply(DruidDataSource input)
{
Resource resource = new Resource(input.getName(), ResourceType.DATASOURCE);
Action action = Action.READ;
Pair<Resource, Action> key = new Pair<>(resource, action);
if (resourceAccessMap.containsKey(key)) {
return resourceAccessMap.get(key).isAllowed();
} else {
Access access = authorizationInfo.isAuthorized(key.lhs, key.rhs);
resourceAccessMap.put(key, access);
return access.isAllowed();
}
}
}
);
}
} else {
druidDataSources = metadataSegmentManager.getInventory();
}
if (includeDisabled != null) {
return builder.entity(
Collections2.transform(
druidDataSources,
new Function<DruidDataSource, String>()
{
@Override
public String apply(DruidDataSource input)
{
return input.getName();
return dataSourceNamesPostAuth.contains(input.getName());
}
}
)
).build();
} else {
return Response.ok().entity(dataSourceNamesPostAuth).build();
}
if (full != null) {
return builder.entity(druidDataSources).build();
}
List<String> dataSourceNames = Lists.newArrayList(
Iterables.transform(
druidDataSources,
new Function<DruidDataSource, String>()
{
@Override
public String apply(DruidDataSource dataSource)
{
return dataSource.getName();
}
}
)
);
Collections.sort(dataSourceNames);
return builder.entity(dataSourceNames).build();
}
@GET