auth_credentials_test.go 6.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266
  1. package s3api
  2. import (
  3. "reflect"
  4. "testing"
  5. . "github.com/seaweedfs/seaweedfs/weed/s3api/s3_constants"
  6. "github.com/stretchr/testify/assert"
  7. "github.com/seaweedfs/seaweedfs/weed/pb/iam_pb"
  8. jsonpb "google.golang.org/protobuf/encoding/protojson"
  9. )
  10. func TestIdentityListFileFormat(t *testing.T) {
  11. s3ApiConfiguration := &iam_pb.S3ApiConfiguration{}
  12. identity1 := &iam_pb.Identity{
  13. Name: "some_name",
  14. Credentials: []*iam_pb.Credential{
  15. {
  16. AccessKey: "some_access_key1",
  17. SecretKey: "some_secret_key2",
  18. },
  19. },
  20. Actions: []string{
  21. ACTION_ADMIN,
  22. ACTION_READ,
  23. ACTION_WRITE,
  24. },
  25. }
  26. identity2 := &iam_pb.Identity{
  27. Name: "some_read_only_user",
  28. Credentials: []*iam_pb.Credential{
  29. {
  30. AccessKey: "some_access_key1",
  31. SecretKey: "some_secret_key1",
  32. },
  33. },
  34. Actions: []string{
  35. ACTION_READ,
  36. },
  37. }
  38. identity3 := &iam_pb.Identity{
  39. Name: "some_normal_user",
  40. Credentials: []*iam_pb.Credential{
  41. {
  42. AccessKey: "some_access_key2",
  43. SecretKey: "some_secret_key2",
  44. },
  45. },
  46. Actions: []string{
  47. ACTION_READ,
  48. ACTION_WRITE,
  49. },
  50. }
  51. s3ApiConfiguration.Identities = append(s3ApiConfiguration.Identities, identity1)
  52. s3ApiConfiguration.Identities = append(s3ApiConfiguration.Identities, identity2)
  53. s3ApiConfiguration.Identities = append(s3ApiConfiguration.Identities, identity3)
  54. m := jsonpb.MarshalOptions{
  55. EmitUnpopulated: true,
  56. Indent: " ",
  57. }
  58. text, _ := m.Marshal(s3ApiConfiguration)
  59. println(string(text))
  60. }
  61. func TestCanDo(t *testing.T) {
  62. ident1 := &Identity{
  63. Name: "anything",
  64. Actions: []Action{
  65. "Write:bucket1/a/b/c/*",
  66. "Write:bucket1/a/b/other",
  67. },
  68. }
  69. // object specific
  70. assert.Equal(t, true, ident1.canDo(ACTION_WRITE, "bucket1", "/a/b/c/d.txt"))
  71. assert.Equal(t, true, ident1.canDo(ACTION_WRITE, "bucket1", "/a/b/c/d/e.txt"))
  72. assert.Equal(t, false, ident1.canDo(ACTION_DELETE_BUCKET, "bucket1", ""))
  73. assert.Equal(t, false, ident1.canDo(ACTION_WRITE, "bucket1", "/a/b/other/some"), "action without *")
  74. assert.Equal(t, false, ident1.canDo(ACTION_WRITE, "bucket1", "/a/b/*"), "action on parent directory")
  75. // bucket specific
  76. ident2 := &Identity{
  77. Name: "anything",
  78. Actions: []Action{
  79. "Read:bucket1",
  80. "Write:bucket1/*",
  81. "WriteAcp:bucket1",
  82. },
  83. }
  84. assert.Equal(t, true, ident2.canDo(ACTION_READ, "bucket1", "/a/b/c/d.txt"))
  85. assert.Equal(t, true, ident2.canDo(ACTION_WRITE, "bucket1", "/a/b/c/d.txt"))
  86. assert.Equal(t, true, ident2.canDo(ACTION_WRITE_ACP, "bucket1", ""))
  87. assert.Equal(t, false, ident2.canDo(ACTION_READ_ACP, "bucket1", ""))
  88. assert.Equal(t, false, ident2.canDo(ACTION_LIST, "bucket1", "/a/b/c/d.txt"))
  89. // across buckets
  90. ident3 := &Identity{
  91. Name: "anything",
  92. Actions: []Action{
  93. "Read",
  94. "Write",
  95. },
  96. }
  97. assert.Equal(t, true, ident3.canDo(ACTION_READ, "bucket1", "/a/b/c/d.txt"))
  98. assert.Equal(t, true, ident3.canDo(ACTION_WRITE, "bucket1", "/a/b/c/d.txt"))
  99. assert.Equal(t, false, ident3.canDo(ACTION_LIST, "bucket1", "/a/b/other/some"))
  100. assert.Equal(t, false, ident3.canDo(ACTION_WRITE_ACP, "bucket1", ""))
  101. // partial buckets
  102. ident4 := &Identity{
  103. Name: "anything",
  104. Actions: []Action{
  105. "Read:special_*",
  106. "ReadAcp:special_*",
  107. },
  108. }
  109. assert.Equal(t, true, ident4.canDo(ACTION_READ, "special_bucket", "/a/b/c/d.txt"))
  110. assert.Equal(t, true, ident4.canDo(ACTION_READ_ACP, "special_bucket", ""))
  111. assert.Equal(t, false, ident4.canDo(ACTION_READ, "bucket1", "/a/b/c/d.txt"))
  112. // admin buckets
  113. ident5 := &Identity{
  114. Name: "anything",
  115. Actions: []Action{
  116. "Admin:special_*",
  117. },
  118. }
  119. assert.Equal(t, true, ident5.canDo(ACTION_READ, "special_bucket", "/a/b/c/d.txt"))
  120. assert.Equal(t, true, ident5.canDo(ACTION_READ_ACP, "special_bucket", ""))
  121. assert.Equal(t, true, ident5.canDo(ACTION_WRITE, "special_bucket", "/a/b/c/d.txt"))
  122. assert.Equal(t, true, ident5.canDo(ACTION_WRITE_ACP, "special_bucket", ""))
  123. // anonymous buckets
  124. ident6 := &Identity{
  125. Name: "anonymous",
  126. Actions: []Action{
  127. "Read",
  128. },
  129. }
  130. assert.Equal(t, true, ident6.canDo(ACTION_READ, "anything_bucket", "/a/b/c/d.txt"))
  131. //test deleteBucket operation
  132. ident7 := &Identity{
  133. Name: "anything",
  134. Actions: []Action{
  135. "DeleteBucket:bucket1",
  136. },
  137. }
  138. assert.Equal(t, true, ident7.canDo(ACTION_DELETE_BUCKET, "bucket1", ""))
  139. }
  140. type LoadS3ApiConfigurationTestCase struct {
  141. pbAccount *iam_pb.Account
  142. pbIdent *iam_pb.Identity
  143. expectIdent *Identity
  144. }
  145. func TestLoadS3ApiConfiguration(t *testing.T) {
  146. specifiedAccount := Account{
  147. Id: "specifiedAccountID",
  148. DisplayName: "specifiedAccountName",
  149. EmailAddress: "specifiedAccounEmail@example.com",
  150. }
  151. pbSpecifiedAccount := iam_pb.Account{
  152. Id: "specifiedAccountID",
  153. DisplayName: "specifiedAccountName",
  154. EmailAddress: "specifiedAccounEmail@example.com",
  155. }
  156. testCases := map[string]*LoadS3ApiConfigurationTestCase{
  157. "notSpecifyAccountId": {
  158. pbIdent: &iam_pb.Identity{
  159. Name: "notSpecifyAccountId",
  160. Actions: []string{
  161. "Read",
  162. "Write",
  163. },
  164. Credentials: []*iam_pb.Credential{
  165. {
  166. AccessKey: "some_access_key1",
  167. SecretKey: "some_secret_key2",
  168. },
  169. },
  170. },
  171. expectIdent: &Identity{
  172. Name: "notSpecifyAccountId",
  173. Account: &AccountAdmin,
  174. Actions: []Action{
  175. "Read",
  176. "Write",
  177. },
  178. Credentials: []*Credential{
  179. {
  180. AccessKey: "some_access_key1",
  181. SecretKey: "some_secret_key2",
  182. },
  183. },
  184. },
  185. },
  186. "specifiedAccountID": {
  187. pbAccount: &pbSpecifiedAccount,
  188. pbIdent: &iam_pb.Identity{
  189. Name: "specifiedAccountID",
  190. Account: &pbSpecifiedAccount,
  191. Actions: []string{
  192. "Read",
  193. "Write",
  194. },
  195. },
  196. expectIdent: &Identity{
  197. Name: "specifiedAccountID",
  198. Account: &specifiedAccount,
  199. Actions: []Action{
  200. "Read",
  201. "Write",
  202. },
  203. },
  204. },
  205. "anonymous": {
  206. pbIdent: &iam_pb.Identity{
  207. Name: "anonymous",
  208. Actions: []string{
  209. "Read",
  210. "Write",
  211. },
  212. },
  213. expectIdent: &Identity{
  214. Name: "anonymous",
  215. Account: &AccountAnonymous,
  216. Actions: []Action{
  217. "Read",
  218. "Write",
  219. },
  220. },
  221. },
  222. }
  223. config := &iam_pb.S3ApiConfiguration{
  224. Identities: make([]*iam_pb.Identity, 0),
  225. }
  226. for _, v := range testCases {
  227. config.Identities = append(config.Identities, v.pbIdent)
  228. if v.pbAccount != nil {
  229. config.Accounts = append(config.Accounts, v.pbAccount)
  230. }
  231. }
  232. iam := IdentityAccessManagement{}
  233. err := iam.loadS3ApiConfiguration(config)
  234. if err != nil {
  235. return
  236. }
  237. for _, ident := range iam.identities {
  238. tc := testCases[ident.Name]
  239. if !reflect.DeepEqual(ident, tc.expectIdent) {
  240. t.Errorf("not expect for ident name %s", ident.Name)
  241. }
  242. }
  243. }