1/* 2 * Licensed to the Apache Software Foundation (ASF) under one or more 3 * contributor license agreements. See the NOTICE file distributed with 4 * this work for additional information regarding copyright ownership. 5 * The ASF licenses this file to You under the Apache License, Version 2.0 6 * (the "License"); you may not use this file except in compliance with 7 * the License. You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 */ 17 18package org.apache.spark 19 20import java.io.File 21 22import org.apache.spark.security.GroupMappingServiceProvider 23import org.apache.spark.util.{ResetSystemProperties, SparkConfWithEnv, Utils} 24 25class DummyGroupMappingServiceProvider extends GroupMappingServiceProvider { 26 27 val userGroups: Set[String] = Set[String]("group1", "group2", "group3") 28 29 override def getGroups(username: String): Set[String] = { 30 userGroups 31 } 32} 33 34class SecurityManagerSuite extends SparkFunSuite with ResetSystemProperties { 35 36 test("set security with conf") { 37 val conf = new SparkConf 38 conf.set("spark.authenticate", "true") 39 conf.set("spark.authenticate.secret", "good") 40 conf.set("spark.ui.acls.enable", "true") 41 conf.set("spark.ui.view.acls", "user1,user2") 42 val securityManager = new SecurityManager(conf); 43 assert(securityManager.isAuthenticationEnabled() === true) 44 assert(securityManager.aclsEnabled() === true) 45 assert(securityManager.checkUIViewPermissions("user1") === true) 46 assert(securityManager.checkUIViewPermissions("user2") === true) 47 assert(securityManager.checkUIViewPermissions("user3") === false) 48 } 49 50 test("set security with conf for groups") { 51 val conf = new SparkConf 52 conf.set("spark.authenticate", "true") 53 conf.set("spark.authenticate.secret", "good") 54 conf.set("spark.ui.acls.enable", "true") 55 conf.set("spark.ui.view.acls.groups", "group1,group2") 56 // default ShellBasedGroupsMappingProvider is used to resolve user groups 57 val securityManager = new SecurityManager(conf); 58 // assuming executing user does not belong to group1,group2 59 assert(securityManager.checkUIViewPermissions("user1") === false) 60 assert(securityManager.checkUIViewPermissions("user2") === false) 61 62 val conf2 = new SparkConf 63 conf2.set("spark.authenticate", "true") 64 conf2.set("spark.authenticate.secret", "good") 65 conf2.set("spark.ui.acls.enable", "true") 66 conf2.set("spark.ui.view.acls.groups", "group1,group2") 67 // explicitly specify a custom GroupsMappingServiceProvider 68 conf2.set("spark.user.groups.mapping", "org.apache.spark.DummyGroupMappingServiceProvider") 69 70 val securityManager2 = new SecurityManager(conf2); 71 // group4,group5 do not match 72 assert(securityManager2.checkUIViewPermissions("user1") === true) 73 assert(securityManager2.checkUIViewPermissions("user2") === true) 74 75 val conf3 = new SparkConf 76 conf3.set("spark.authenticate", "true") 77 conf3.set("spark.authenticate.secret", "good") 78 conf3.set("spark.ui.acls.enable", "true") 79 conf3.set("spark.ui.view.acls.groups", "group4,group5") 80 // explicitly specify a bogus GroupsMappingServiceProvider 81 conf3.set("spark.user.groups.mapping", "BogusServiceProvider") 82 83 val securityManager3 = new SecurityManager(conf3); 84 // BogusServiceProvider cannot be loaded and an error is logged returning an empty group set 85 assert(securityManager3.checkUIViewPermissions("user1") === false) 86 assert(securityManager3.checkUIViewPermissions("user2") === false) 87 } 88 89 test("set security with api") { 90 val conf = new SparkConf 91 conf.set("spark.ui.view.acls", "user1,user2") 92 val securityManager = new SecurityManager(conf); 93 securityManager.setAcls(true) 94 assert(securityManager.aclsEnabled() === true) 95 securityManager.setAcls(false) 96 assert(securityManager.aclsEnabled() === false) 97 98 // acls are off so doesn't matter what view acls set to 99 assert(securityManager.checkUIViewPermissions("user4") === true) 100 101 securityManager.setAcls(true) 102 assert(securityManager.aclsEnabled() === true) 103 securityManager.setViewAcls(Set[String]("user5"), "user6,user7") 104 assert(securityManager.checkUIViewPermissions("user1") === false) 105 assert(securityManager.checkUIViewPermissions("user5") === true) 106 assert(securityManager.checkUIViewPermissions("user6") === true) 107 assert(securityManager.checkUIViewPermissions("user7") === true) 108 assert(securityManager.checkUIViewPermissions("user8") === false) 109 assert(securityManager.checkUIViewPermissions(null) === true) 110 } 111 112 test("set security with api for groups") { 113 val conf = new SparkConf 114 conf.set("spark.user.groups.mapping", "org.apache.spark.DummyGroupMappingServiceProvider") 115 116 val securityManager = new SecurityManager(conf); 117 securityManager.setAcls(true) 118 securityManager.setViewAclsGroups("group1,group2") 119 120 // group1,group2 match 121 assert(securityManager.checkUIViewPermissions("user1") === true) 122 assert(securityManager.checkUIViewPermissions("user2") === true) 123 124 // change groups so they do not match 125 securityManager.setViewAclsGroups("group4,group5") 126 assert(securityManager.checkUIViewPermissions("user1") === false) 127 assert(securityManager.checkUIViewPermissions("user2") === false) 128 129 val conf2 = new SparkConf 130 conf.set("spark.user.groups.mapping", "BogusServiceProvider") 131 132 val securityManager2 = new SecurityManager(conf2) 133 securityManager2.setAcls(true) 134 securityManager2.setViewAclsGroups("group1,group2") 135 136 // group1,group2 do not match because of BogusServiceProvider 137 assert(securityManager.checkUIViewPermissions("user1") === false) 138 assert(securityManager.checkUIViewPermissions("user2") === false) 139 140 // setting viewAclsGroups to empty should still not match because of BogusServiceProvider 141 securityManager2.setViewAclsGroups("") 142 assert(securityManager.checkUIViewPermissions("user1") === false) 143 assert(securityManager.checkUIViewPermissions("user2") === false) 144 } 145 146 test("set security modify acls") { 147 val conf = new SparkConf 148 conf.set("spark.modify.acls", "user1,user2") 149 150 val securityManager = new SecurityManager(conf); 151 securityManager.setAcls(true) 152 assert(securityManager.aclsEnabled() === true) 153 securityManager.setAcls(false) 154 assert(securityManager.aclsEnabled() === false) 155 156 // acls are off so doesn't matter what view acls set to 157 assert(securityManager.checkModifyPermissions("user4") === true) 158 159 securityManager.setAcls(true) 160 assert(securityManager.aclsEnabled() === true) 161 securityManager.setModifyAcls(Set("user5"), "user6,user7") 162 assert(securityManager.checkModifyPermissions("user1") === false) 163 assert(securityManager.checkModifyPermissions("user5") === true) 164 assert(securityManager.checkModifyPermissions("user6") === true) 165 assert(securityManager.checkModifyPermissions("user7") === true) 166 assert(securityManager.checkModifyPermissions("user8") === false) 167 assert(securityManager.checkModifyPermissions(null) === true) 168 } 169 170 test("set security modify acls for groups") { 171 val conf = new SparkConf 172 conf.set("spark.user.groups.mapping", "org.apache.spark.DummyGroupMappingServiceProvider") 173 174 val securityManager = new SecurityManager(conf); 175 securityManager.setAcls(true) 176 securityManager.setModifyAclsGroups("group1,group2") 177 178 // group1,group2 match 179 assert(securityManager.checkModifyPermissions("user1") === true) 180 assert(securityManager.checkModifyPermissions("user2") === true) 181 182 // change groups so they do not match 183 securityManager.setModifyAclsGroups("group4,group5") 184 assert(securityManager.checkModifyPermissions("user1") === false) 185 assert(securityManager.checkModifyPermissions("user2") === false) 186 187 // change so they match again 188 securityManager.setModifyAclsGroups("group2,group3") 189 assert(securityManager.checkModifyPermissions("user1") === true) 190 assert(securityManager.checkModifyPermissions("user2") === true) 191 } 192 193 test("set security admin acls") { 194 val conf = new SparkConf 195 conf.set("spark.admin.acls", "user1,user2") 196 conf.set("spark.ui.view.acls", "user3") 197 conf.set("spark.modify.acls", "user4") 198 199 val securityManager = new SecurityManager(conf); 200 securityManager.setAcls(true) 201 assert(securityManager.aclsEnabled() === true) 202 203 assert(securityManager.checkModifyPermissions("user1") === true) 204 assert(securityManager.checkModifyPermissions("user2") === true) 205 assert(securityManager.checkModifyPermissions("user4") === true) 206 assert(securityManager.checkModifyPermissions("user3") === false) 207 assert(securityManager.checkModifyPermissions("user5") === false) 208 assert(securityManager.checkModifyPermissions(null) === true) 209 assert(securityManager.checkUIViewPermissions("user1") === true) 210 assert(securityManager.checkUIViewPermissions("user2") === true) 211 assert(securityManager.checkUIViewPermissions("user3") === true) 212 assert(securityManager.checkUIViewPermissions("user4") === false) 213 assert(securityManager.checkUIViewPermissions("user5") === false) 214 assert(securityManager.checkUIViewPermissions(null) === true) 215 216 securityManager.setAdminAcls("user6") 217 securityManager.setViewAcls(Set[String]("user8"), "user9") 218 securityManager.setModifyAcls(Set("user11"), "user9") 219 assert(securityManager.checkModifyPermissions("user6") === true) 220 assert(securityManager.checkModifyPermissions("user11") === true) 221 assert(securityManager.checkModifyPermissions("user9") === true) 222 assert(securityManager.checkModifyPermissions("user1") === false) 223 assert(securityManager.checkModifyPermissions("user4") === false) 224 assert(securityManager.checkModifyPermissions(null) === true) 225 assert(securityManager.checkUIViewPermissions("user6") === true) 226 assert(securityManager.checkUIViewPermissions("user8") === true) 227 assert(securityManager.checkUIViewPermissions("user9") === true) 228 assert(securityManager.checkUIViewPermissions("user1") === false) 229 assert(securityManager.checkUIViewPermissions("user3") === false) 230 assert(securityManager.checkUIViewPermissions(null) === true) 231 } 232 233 test("set security admin acls for groups") { 234 val conf = new SparkConf 235 conf.set("spark.admin.acls.groups", "group1") 236 conf.set("spark.ui.view.acls.groups", "group2") 237 conf.set("spark.modify.acls.groups", "group3") 238 conf.set("spark.user.groups.mapping", "org.apache.spark.DummyGroupMappingServiceProvider") 239 240 val securityManager = new SecurityManager(conf); 241 securityManager.setAcls(true) 242 assert(securityManager.aclsEnabled() === true) 243 244 // group1,group2,group3 match 245 assert(securityManager.checkModifyPermissions("user1") === true) 246 assert(securityManager.checkUIViewPermissions("user1") === true) 247 248 // change admin groups so they do not match. view and modify groups are set to admin groups 249 securityManager.setAdminAclsGroups("group4,group5") 250 // invoke the set ui and modify to propagate the changes 251 securityManager.setViewAclsGroups("") 252 securityManager.setModifyAclsGroups("") 253 254 assert(securityManager.checkModifyPermissions("user1") === false) 255 assert(securityManager.checkUIViewPermissions("user1") === false) 256 257 // change modify groups so they match 258 securityManager.setModifyAclsGroups("group3") 259 assert(securityManager.checkModifyPermissions("user1") === true) 260 assert(securityManager.checkUIViewPermissions("user1") === false) 261 262 // change view groups so they match 263 securityManager.setViewAclsGroups("group2") 264 securityManager.setModifyAclsGroups("group4") 265 assert(securityManager.checkModifyPermissions("user1") === false) 266 assert(securityManager.checkUIViewPermissions("user1") === true) 267 268 // change modify and view groups so they do not match 269 securityManager.setViewAclsGroups("group7") 270 securityManager.setModifyAclsGroups("group8") 271 assert(securityManager.checkModifyPermissions("user1") === false) 272 assert(securityManager.checkUIViewPermissions("user1") === false) 273 } 274 275 test("set security with * in acls") { 276 val conf = new SparkConf 277 conf.set("spark.ui.acls.enable", "true") 278 conf.set("spark.admin.acls", "user1,user2") 279 conf.set("spark.ui.view.acls", "*") 280 conf.set("spark.modify.acls", "user4") 281 282 val securityManager = new SecurityManager(conf) 283 assert(securityManager.aclsEnabled() === true) 284 285 // check for viewAcls with * 286 assert(securityManager.checkUIViewPermissions("user1") === true) 287 assert(securityManager.checkUIViewPermissions("user5") === true) 288 assert(securityManager.checkUIViewPermissions("user6") === true) 289 assert(securityManager.checkModifyPermissions("user4") === true) 290 assert(securityManager.checkModifyPermissions("user7") === false) 291 assert(securityManager.checkModifyPermissions("user8") === false) 292 293 // check for modifyAcls with * 294 securityManager.setModifyAcls(Set("user4"), "*") 295 assert(securityManager.checkModifyPermissions("user7") === true) 296 assert(securityManager.checkModifyPermissions("user8") === true) 297 298 securityManager.setAdminAcls("user1,user2") 299 securityManager.setModifyAcls(Set("user1"), "user2") 300 securityManager.setViewAcls(Set("user1"), "user2") 301 assert(securityManager.checkUIViewPermissions("user5") === false) 302 assert(securityManager.checkUIViewPermissions("user6") === false) 303 assert(securityManager.checkModifyPermissions("user7") === false) 304 assert(securityManager.checkModifyPermissions("user8") === false) 305 306 // check for adminAcls with * 307 securityManager.setAdminAcls("user1,*") 308 securityManager.setModifyAcls(Set("user1"), "user2") 309 securityManager.setViewAcls(Set("user1"), "user2") 310 assert(securityManager.checkUIViewPermissions("user5") === true) 311 assert(securityManager.checkUIViewPermissions("user6") === true) 312 assert(securityManager.checkModifyPermissions("user7") === true) 313 assert(securityManager.checkModifyPermissions("user8") === true) 314 } 315 316 test("set security with * in acls for groups") { 317 val conf = new SparkConf 318 conf.set("spark.ui.acls.enable", "true") 319 conf.set("spark.admin.acls.groups", "group4,group5") 320 conf.set("spark.ui.view.acls.groups", "*") 321 conf.set("spark.modify.acls.groups", "group6") 322 323 val securityManager = new SecurityManager(conf) 324 assert(securityManager.aclsEnabled() === true) 325 326 // check for viewAclsGroups with * 327 assert(securityManager.checkUIViewPermissions("user1") === true) 328 assert(securityManager.checkUIViewPermissions("user2") === true) 329 assert(securityManager.checkModifyPermissions("user1") === false) 330 assert(securityManager.checkModifyPermissions("user2") === false) 331 332 // check for modifyAcls with * 333 securityManager.setModifyAclsGroups("*") 334 securityManager.setViewAclsGroups("group6") 335 assert(securityManager.checkUIViewPermissions("user1") === false) 336 assert(securityManager.checkUIViewPermissions("user2") === false) 337 assert(securityManager.checkModifyPermissions("user1") === true) 338 assert(securityManager.checkModifyPermissions("user2") === true) 339 340 // check for adminAcls with * 341 securityManager.setAdminAclsGroups("group9,*") 342 securityManager.setModifyAclsGroups("group4,group5") 343 securityManager.setViewAclsGroups("group6,group7") 344 assert(securityManager.checkUIViewPermissions("user5") === true) 345 assert(securityManager.checkUIViewPermissions("user6") === true) 346 assert(securityManager.checkModifyPermissions("user7") === true) 347 assert(securityManager.checkModifyPermissions("user8") === true) 348 } 349 350 test("security for groups default behavior") { 351 // no groups or userToGroupsMapper provided 352 // this will default to the ShellBasedGroupsMappingProvider 353 val conf = new SparkConf 354 355 val securityManager = new SecurityManager(conf) 356 securityManager.setAcls(true) 357 358 assert(securityManager.checkUIViewPermissions("user1") === false) 359 assert(securityManager.checkModifyPermissions("user1") === false) 360 361 // set groups only 362 securityManager.setAdminAclsGroups("group1,group2") 363 assert(securityManager.checkUIViewPermissions("user1") === false) 364 assert(securityManager.checkModifyPermissions("user1") === false) 365 } 366 367 test("ssl on setup") { 368 val conf = SSLSampleConfigs.sparkSSLConfig() 369 val expectedAlgorithms = Set( 370 "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384", 371 "TLS_RSA_WITH_AES_256_CBC_SHA256", 372 "TLS_DHE_RSA_WITH_AES_256_CBC_SHA256", 373 "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256", 374 "TLS_DHE_RSA_WITH_AES_128_CBC_SHA256", 375 "SSL_ECDHE_RSA_WITH_AES_256_CBC_SHA384", 376 "SSL_RSA_WITH_AES_256_CBC_SHA256", 377 "SSL_DHE_RSA_WITH_AES_256_CBC_SHA256", 378 "SSL_ECDHE_RSA_WITH_AES_128_CBC_SHA256", 379 "SSL_DHE_RSA_WITH_AES_128_CBC_SHA256") 380 381 val securityManager = new SecurityManager(conf) 382 383 assert(securityManager.fileServerSSLOptions.enabled === true) 384 385 assert(securityManager.sslSocketFactory.isDefined === true) 386 assert(securityManager.hostnameVerifier.isDefined === true) 387 388 assert(securityManager.fileServerSSLOptions.trustStore.isDefined === true) 389 assert(securityManager.fileServerSSLOptions.trustStore.get.getName === "truststore") 390 assert(securityManager.fileServerSSLOptions.keyStore.isDefined === true) 391 assert(securityManager.fileServerSSLOptions.keyStore.get.getName === "keystore") 392 assert(securityManager.fileServerSSLOptions.trustStorePassword === Some("password")) 393 assert(securityManager.fileServerSSLOptions.keyStorePassword === Some("password")) 394 assert(securityManager.fileServerSSLOptions.keyPassword === Some("password")) 395 assert(securityManager.fileServerSSLOptions.protocol === Some("TLSv1.2")) 396 assert(securityManager.fileServerSSLOptions.enabledAlgorithms === expectedAlgorithms) 397 } 398 399 test("ssl off setup") { 400 val file = File.createTempFile("SSLOptionsSuite", "conf", Utils.createTempDir()) 401 402 System.setProperty("spark.ssl.configFile", file.getAbsolutePath) 403 val conf = new SparkConf() 404 405 val securityManager = new SecurityManager(conf) 406 407 assert(securityManager.fileServerSSLOptions.enabled === false) 408 assert(securityManager.sslSocketFactory.isDefined === false) 409 assert(securityManager.hostnameVerifier.isDefined === false) 410 } 411 412 test("missing secret authentication key") { 413 val conf = new SparkConf().set("spark.authenticate", "true") 414 intercept[IllegalArgumentException] { 415 new SecurityManager(conf) 416 } 417 } 418 419 test("secret authentication key") { 420 val key = "very secret key" 421 val conf = new SparkConf() 422 .set(SecurityManager.SPARK_AUTH_CONF, "true") 423 .set(SecurityManager.SPARK_AUTH_SECRET_CONF, key) 424 assert(key === new SecurityManager(conf).getSecretKey()) 425 426 val keyFromEnv = "very secret key from env" 427 val conf2 = new SparkConfWithEnv(Map(SecurityManager.ENV_AUTH_SECRET -> keyFromEnv)) 428 .set(SecurityManager.SPARK_AUTH_CONF, "true") 429 .set(SecurityManager.SPARK_AUTH_SECRET_CONF, key) 430 assert(keyFromEnv === new SecurityManager(conf2).getSecretKey()) 431 } 432 433} 434 435