YARN-2059. Added admin ACLs support to Timeline Server. Contributed by Zhijie Shen.
git-svn-id: https://svn.apache.org/repos/asf/hadoop/common/trunk@1597207 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
6c56612af5
commit
7f0724dddb
|
@ -102,6 +102,9 @@ Release 2.5.0 - UNRELEASED
|
|||
YARN-2012. Fair Scheduler: allow default queue placement rule to take an
|
||||
arbitrary queue (Ashwin Shankar via Sandy Ryza)
|
||||
|
||||
YARN-2059. Added admin ACLs support to Timeline Server. (Zhijie Shen via
|
||||
vinodkv)
|
||||
|
||||
OPTIMIZATIONS
|
||||
|
||||
BUG FIXES
|
||||
|
|
|
@ -27,8 +27,8 @@ import org.apache.hadoop.classification.InterfaceAudience.Private;
|
|||
import org.apache.hadoop.conf.Configuration;
|
||||
import org.apache.hadoop.security.UserGroupInformation;
|
||||
import org.apache.hadoop.yarn.api.records.timeline.TimelineEntity;
|
||||
import org.apache.hadoop.yarn.conf.YarnConfiguration;
|
||||
import org.apache.hadoop.yarn.exceptions.YarnException;
|
||||
import org.apache.hadoop.yarn.security.AdminACLsManager;
|
||||
import org.apache.hadoop.yarn.server.applicationhistoryservice.timeline.EntityIdentifier;
|
||||
import org.apache.hadoop.yarn.server.applicationhistoryservice.timeline.TimelineStore.SystemFilter;
|
||||
|
||||
|
@ -42,11 +42,10 @@ public class TimelineACLsManager {
|
|||
|
||||
private static final Log LOG = LogFactory.getLog(TimelineACLsManager.class);
|
||||
|
||||
private boolean aclsEnabled;
|
||||
private AdminACLsManager adminAclsManager;
|
||||
|
||||
public TimelineACLsManager(Configuration conf) {
|
||||
aclsEnabled = conf.getBoolean(YarnConfiguration.YARN_ACL_ENABLE,
|
||||
YarnConfiguration.DEFAULT_YARN_ACL_ENABLE);
|
||||
this.adminAclsManager = new AdminACLsManager(conf);
|
||||
}
|
||||
|
||||
public boolean checkAccess(UserGroupInformation callerUGI,
|
||||
|
@ -57,7 +56,7 @@ public class TimelineACLsManager {
|
|||
+ new EntityIdentifier(entity.getEntityId(), entity.getEntityType()));
|
||||
}
|
||||
|
||||
if (!aclsEnabled) {
|
||||
if (!adminAclsManager.areACLsEnabled()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -70,10 +69,12 @@ public class TimelineACLsManager {
|
|||
+ " is corrupted.");
|
||||
}
|
||||
String owner = values.iterator().next().toString();
|
||||
// TODO: Currently we just check the user is the timeline entity owner. In
|
||||
// the future, we need to check whether the user is admin or is in the
|
||||
// TODO: Currently we just check the user is the admin or the timeline
|
||||
// entity owner. In the future, we need to check whether the user is in the
|
||||
// allowed user/group list
|
||||
if (callerUGI != null && callerUGI.getShortUserName().equals(owner)) {
|
||||
if (callerUGI != null
|
||||
&& (adminAclsManager.isAdmin(callerUGI) ||
|
||||
callerUGI.getShortUserName().equals(owner))) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
|
@ -81,8 +82,11 @@ public class TimelineACLsManager {
|
|||
|
||||
@Private
|
||||
@VisibleForTesting
|
||||
public void setACLsEnabled(boolean aclsEnabled) {
|
||||
this.aclsEnabled = aclsEnabled;
|
||||
public AdminACLsManager
|
||||
setAdminACLsManager(AdminACLsManager adminAclsManager) {
|
||||
AdminACLsManager oldAdminACLsManager = this.adminAclsManager;
|
||||
this.adminAclsManager = adminAclsManager;
|
||||
return oldAdminACLsManager;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -346,8 +346,9 @@ public class TimelineWebServices {
|
|||
new EntityIdentifier(entity.getEntityId(), entity.getEntityType());
|
||||
|
||||
// check if there is existing entity
|
||||
TimelineEntity existingEntity = null;
|
||||
try {
|
||||
TimelineEntity existingEntity =
|
||||
existingEntity =
|
||||
store.getEntity(entityID.getId(), entityID.getType(),
|
||||
EnumSet.of(Field.PRIMARY_FILTERS));
|
||||
if (existingEntity != null
|
||||
|
@ -369,10 +370,14 @@ public class TimelineWebServices {
|
|||
continue;
|
||||
}
|
||||
|
||||
// inject owner information for the access check
|
||||
// inject owner information for the access check if this is the first
|
||||
// time to post the entity, in case it's the admin who is updating
|
||||
// the timeline data.
|
||||
try {
|
||||
injectOwnerInfo(entity,
|
||||
callerUGI == null ? "" : callerUGI.getShortUserName());
|
||||
if (existingEntity == null) {
|
||||
injectOwnerInfo(entity,
|
||||
callerUGI == null ? "" : callerUGI.getShortUserName());
|
||||
}
|
||||
} catch (YarnException e) {
|
||||
// Skip the entity which messes up the primary filter and record the
|
||||
// error
|
||||
|
|
|
@ -49,6 +49,7 @@ public class TestTimelineACLsManager {
|
|||
public void testYarnACLsEnabled() throws Exception {
|
||||
Configuration conf = new YarnConfiguration();
|
||||
conf.setBoolean(YarnConfiguration.YARN_ACL_ENABLE, true);
|
||||
conf.set(YarnConfiguration.YARN_ADMIN_ACL, "admin");
|
||||
TimelineACLsManager timelineACLsManager =
|
||||
new TimelineACLsManager(conf);
|
||||
TimelineEntity entity = new TimelineEntity();
|
||||
|
@ -63,12 +64,17 @@ public class TestTimelineACLsManager {
|
|||
"Other shouldn't be allowed to access",
|
||||
timelineACLsManager.checkAccess(
|
||||
UserGroupInformation.createRemoteUser("other"), entity));
|
||||
Assert.assertTrue(
|
||||
"Admin should be allowed to access",
|
||||
timelineACLsManager.checkAccess(
|
||||
UserGroupInformation.createRemoteUser("admin"), entity));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCorruptedOwnerInfo() throws Exception {
|
||||
Configuration conf = new YarnConfiguration();
|
||||
conf.setBoolean(YarnConfiguration.YARN_ACL_ENABLE, true);
|
||||
conf.set(YarnConfiguration.YARN_ADMIN_ACL, "owner");
|
||||
TimelineACLsManager timelineACLsManager =
|
||||
new TimelineACLsManager(conf);
|
||||
TimelineEntity entity = new TimelineEntity();
|
||||
|
|
|
@ -40,6 +40,7 @@ import org.apache.hadoop.yarn.api.records.timeline.TimelineEvent;
|
|||
import org.apache.hadoop.yarn.api.records.timeline.TimelineEvents;
|
||||
import org.apache.hadoop.yarn.api.records.timeline.TimelinePutResponse;
|
||||
import org.apache.hadoop.yarn.conf.YarnConfiguration;
|
||||
import org.apache.hadoop.yarn.security.AdminACLsManager;
|
||||
import org.apache.hadoop.yarn.server.applicationhistoryservice.timeline.TestMemoryTimelineStore;
|
||||
import org.apache.hadoop.yarn.server.applicationhistoryservice.timeline.TimelineStore;
|
||||
import org.apache.hadoop.yarn.server.applicationhistoryservice.timeline.security.TimelineACLsManager;
|
||||
|
@ -64,6 +65,7 @@ public class TestTimelineWebServices extends JerseyTest {
|
|||
|
||||
private static TimelineStore store;
|
||||
private static TimelineACLsManager timelineACLsManager;
|
||||
private static AdminACLsManager adminACLsManager;
|
||||
private static String remoteUser;
|
||||
private long beforeTime;
|
||||
|
||||
|
@ -83,6 +85,9 @@ public class TestTimelineWebServices extends JerseyTest {
|
|||
Configuration conf = new YarnConfiguration();
|
||||
conf.setBoolean(YarnConfiguration.YARN_ACL_ENABLE, false);
|
||||
timelineACLsManager = new TimelineACLsManager(conf);
|
||||
conf.setBoolean(YarnConfiguration.YARN_ACL_ENABLE, true);
|
||||
conf.set(YarnConfiguration.YARN_ADMIN_ACL, "admin");
|
||||
adminACLsManager = new AdminACLsManager(conf);
|
||||
bind(TimelineACLsManager.class).toInstance(timelineACLsManager);
|
||||
serve("/*").with(GuiceContainer.class);
|
||||
filter("/*").through(TestFilter.class);
|
||||
|
@ -387,7 +392,8 @@ public class TestTimelineWebServices extends JerseyTest {
|
|||
|
||||
@Test
|
||||
public void testPostEntitiesWithYarnACLsEnabled() throws Exception {
|
||||
timelineACLsManager.setACLsEnabled(true);
|
||||
AdminACLsManager oldAdminACLsManager =
|
||||
timelineACLsManager.setAdminACLsManager(adminACLsManager);
|
||||
remoteUser = "tester";
|
||||
try {
|
||||
TimelineEntities entities = new TimelineEntities();
|
||||
|
@ -419,14 +425,15 @@ public class TestTimelineWebServices extends JerseyTest {
|
|||
Assert.assertEquals(TimelinePutResponse.TimelinePutError.ACCESS_DENIED,
|
||||
putResponse.getErrors().get(0).getErrorCode());
|
||||
} finally {
|
||||
timelineACLsManager.setACLsEnabled(false);
|
||||
timelineACLsManager.setAdminACLsManager(oldAdminACLsManager);
|
||||
remoteUser = null;
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetEntityWithYarnACLsEnabled() throws Exception {
|
||||
timelineACLsManager.setACLsEnabled(true);
|
||||
AdminACLsManager oldAdminACLsManager =
|
||||
timelineACLsManager.setAdminACLsManager(adminACLsManager);
|
||||
remoteUser = "tester";
|
||||
try {
|
||||
TimelineEntities entities = new TimelineEntities();
|
||||
|
@ -481,14 +488,15 @@ public class TestTimelineWebServices extends JerseyTest {
|
|||
assertEquals(ClientResponse.Status.NOT_FOUND,
|
||||
response.getClientResponseStatus());
|
||||
} finally {
|
||||
timelineACLsManager.setACLsEnabled(false);
|
||||
timelineACLsManager.setAdminACLsManager(oldAdminACLsManager);
|
||||
remoteUser = null;
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetEntitiesWithYarnACLsEnabled() {
|
||||
timelineACLsManager.setACLsEnabled(true);
|
||||
AdminACLsManager oldAdminACLsManager =
|
||||
timelineACLsManager.setAdminACLsManager(adminACLsManager);
|
||||
remoteUser = "tester";
|
||||
try {
|
||||
TimelineEntities entities = new TimelineEntities();
|
||||
|
@ -526,14 +534,15 @@ public class TestTimelineWebServices extends JerseyTest {
|
|||
assertEquals("test type 4", entities.getEntities().get(0).getEntityType());
|
||||
assertEquals("test id 5", entities.getEntities().get(0).getEntityId());
|
||||
} finally {
|
||||
timelineACLsManager.setACLsEnabled(false);
|
||||
timelineACLsManager.setAdminACLsManager(oldAdminACLsManager);
|
||||
remoteUser = null;
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetEventsWithYarnACLsEnabled() {
|
||||
timelineACLsManager.setACLsEnabled(true);
|
||||
AdminACLsManager oldAdminACLsManager =
|
||||
timelineACLsManager.setAdminACLsManager(adminACLsManager);
|
||||
remoteUser = "tester";
|
||||
try {
|
||||
TimelineEntities entities = new TimelineEntities();
|
||||
|
@ -579,7 +588,7 @@ public class TestTimelineWebServices extends JerseyTest {
|
|||
assertEquals(1, events.getAllEvents().size());
|
||||
assertEquals("test id 6", events.getAllEvents().get(0).getEntityId());
|
||||
} finally {
|
||||
timelineACLsManager.setACLsEnabled(false);
|
||||
timelineACLsManager.setAdminACLsManager(oldAdminACLsManager);
|
||||
remoteUser = null;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue