Skip to content

Commit aa748d4

Browse files
committed
Add the newest version of adapter.py and test_adapter.py
1 parent f612bdc commit aa748d4

2 files changed

Lines changed: 233 additions & 11 deletions

File tree

casbin_pymongo_adapter/adapter.py

Lines changed: 122 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,35 +1,146 @@
11
from casbin import persist
22
from pymongo import MongoClient
33

4+
class CasbinRule():
5+
'''
6+
CasbinRule model
7+
'''
8+
9+
__tablename__ = "casbin_rule"
10+
11+
def __init__(self, ptype='', v0='', v1='', v2='', v3='', v4='', v5=''):
12+
self.ptype = ptype
13+
self.v0 = v0
14+
self.v1 = v1
15+
self.v2 = v2
16+
self.v3 = v3
17+
self.v4 = v4
18+
self.v5 = v5
19+
20+
def __str__(self):
21+
dict = {'ptype':self.ptype}
22+
if self.v0:
23+
dict['v0'] = self.v0
24+
if self.v1:
25+
dict['v1'] = self.v1
26+
if self.v2:
27+
dict['v2'] = self.v2
28+
if self.v3:
29+
dict['v3'] = self.v3
30+
if self.v4:
31+
dict['v4'] = self.v4
32+
if self.v5:
33+
dict['v5'] = self.v5
34+
return dict
35+
36+
def __repr__(self):
37+
return '<CasbinRule :"{}">'.format(str(self))
38+
439

540
class Adapter(persist.Adapter):
6-
"""the pymongo adapter for Casbin."""
41+
"""the interface for Casbin adapters."""
742

843
def __init__(self, uri, dbname, collection="casbin_rule"):
944
client = MongoClient(uri)
1045
db = client[dbname]
1146
self._collection = db[collection]
12-
pass
1347

1448
def load_policy(self, model):
15-
"""loads all policy rules from the storage."""
49+
'''
50+
implementing add Interface for casbin \n
51+
load all policy rules from mongodb \n
52+
'''
1653
for lines in self._collection.find():
17-
pass
54+
persist.load_policy_line(str(lines), model)
55+
56+
def _save_policy_line(self, ptype, rule):
57+
line = CasbinRule(ptype=ptype)
58+
if len(rule) > 0:
59+
line.v0 = rule[0]
60+
if len(rule) > 1:
61+
line.v1 = rule[1]
62+
if len(rule) > 2:
63+
line.v2 = rule[2]
64+
if len(rule) > 3:
65+
line.v3 = rule[3]
66+
if len(rule) > 4:
67+
line.v4 = rule[4]
68+
if len(rule) > 5:
69+
line.v5 = rule[5]
70+
document = {
71+
'ptype': line.ptype,
72+
'v0': line.v0,
73+
'v1': line.v1,
74+
'v2': line.v2,
75+
'v3': line.v3,
76+
'v4': line.v4,
77+
'v5': line.v5,
78+
}
79+
# if len(rule) == 1:
80+
# document = {'ptype':ptype,
81+
# 'v0':rule[0]
82+
# }
83+
# elif len(rule) == 2:
84+
# document = {'ptype': ptype,
85+
# 'v0': rule[0],
86+
# 'v1': rule[1]
87+
# }
88+
# elif len(rule) == 3:
89+
# document = {'ptype': ptype,
90+
# 'v0': rule[0],
91+
# 'v1': rule[1],
92+
# 'v2': rule[2]
93+
# }
94+
# elif len(rule) == 4:
95+
# document = {'ptype': ptype,
96+
# 'v0': rule[0],
97+
# 'v1': rule[1],
98+
# 'v2': rule[2],
99+
# 'v3': rule[3]
100+
# }
101+
# elif len(rule) == 5:
102+
# document = {'ptype': ptype,
103+
# 'v0': rule[0],
104+
# 'v1': rule[1],
105+
# 'v2': rule[2],
106+
# 'v3': rule[3],
107+
# 'v4': rule[4]
108+
# }
109+
# else:
110+
# document = {'ptype': ptype,
111+
# 'v0': rule[0],
112+
# 'v1': rule[1],
113+
# 'v2': rule[2],
114+
# 'v3': rule[3],
115+
# 'v4': rule[4],
116+
# 'v5': rule[5]
117+
# }
118+
# self._collection.insert_one(document)
119+
self._collection.insert_one(line)
18120

19121
def save_policy(self, model):
20-
"""saves all policy rules to the storage."""
21-
pass
122+
'''
123+
implementing add Interface for casbin \n
124+
save the policy in mongodb \n
125+
'''
126+
for sec in ["p", "g"]:
127+
if sec not in model.model.keys():
128+
continue
129+
for ptype, ast in model.model[sec].items():
130+
for rule in ast.policy:
131+
self._save_policy_line(ptype, rule)
132+
return True
22133

23134
def add_policy(self, sec, ptype, rule):
24-
"""adds a policy rule to the storage."""
25-
pass
135+
"""add policy rules to mongodb"""
136+
self._save_policy_line(ptype, rule)
26137

27138
def remove_policy(self, sec, ptype, rule):
28-
"""removes a policy rule from the storage."""
139+
"""delete policy rules from mongodb"""
29140
pass
30141

31142
def remove_filtered_policy(self, sec, ptype, field_index, *field_values):
32-
"""removes policy rules that match the filter from the storage.
33-
This is part of the Auto-Save feature.
143+
"""
144+
delete policy rules for matching filters from mongodb
34145
"""
35146
pass

tests/test_adapter.py

Lines changed: 111 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
from casbin_pymongo_adapter.adapter import Adapter
2+
from casbin_pymongo_adapter.adapter import CasbinRule
3+
from unittest import TestCase
4+
import casbin
5+
import os
6+
import simpleeval
7+
8+
def get_fixture(path):
9+
'''
10+
get model path
11+
'''
12+
dir_path = os.path.split(os.path.realpath(__file__))[0] + "/"
13+
return os.path.abspath(dir_path + path)
14+
15+
16+
def get_enforcer():
17+
adapter = Adapter('mongodb://localhost:27017', 'casbin_test')
18+
c1 = CasbinRule(ptype='p', v0='alice', v1='data1', v2='read')
19+
adapter.save_policy(c1)
20+
c2 = CasbinRule(ptype='p', v0='bob', v1='data2', v2='write')
21+
adapter.save_policy(c2)
22+
c3 = CasbinRule(ptype='p', v0='data2_admin', v1='data2', v2='read')
23+
adapter.save_policy(c3)
24+
c4 = CasbinRule(ptype='p', v0='data2_admin', v1='data2', v2='write')
25+
adapter.save_policy(c4)
26+
c5 = CasbinRule(ptype='g', v0='alice', v1='data2_admin')
27+
adapter.save_policy(c5)
28+
29+
return casbin.Enforcer(get_fixture('rbac_model.conf'), adapter, True)
30+
31+
32+
class TestConfig(TestCase):
33+
'''
34+
unittest
35+
'''
36+
37+
def test_enforcer_basic(self):
38+
'''
39+
test policy
40+
'''
41+
e = get_enforcer()
42+
self.assertFalse(e.enforce('alice', 'data1', 'write'))
43+
self.assertFalse(e.enforce('bob', 'data1', 'read'))
44+
self.assertTrue(e.enforce('bob', 'data2', 'write'))
45+
self.assertTrue(e.enforce('alice', 'data2', 'read'))
46+
self.assertTrue(e.enforce('alice', 'data2', 'write'))
47+
48+
def test_add_policy(self):
49+
'''
50+
test add_policy
51+
'''
52+
adapter = Adapter('mongodb://localhost:27017', 'casbin_test')
53+
e = casbin.Enforcer(get_fixture('rbac_model.conf'), adapter, True)
54+
55+
try:
56+
self.assertFalse(e.enforce('alice', 'data1', 'write'))
57+
self.assertFalse(e.enforce('bob', 'data1', 'read'))
58+
self.assertFalse(e.enforce('bob', 'data2', 'write'))
59+
self.assertFalse(e.enforce('alice', 'data2', 'read'))
60+
self.assertFalse(e.enforce('alice', 'data2', 'write'))
61+
except simpleeval.NameNotDefined:
62+
# This is caused by an upstream bug when there is no policy loaded
63+
# Should be resolved in pycasbin >= 0.3
64+
pass
65+
66+
adapter.add_policy(sec=None, ptype='p', rule=['alice', 'data1', 'read'])
67+
adapter.add_policy(sec=None, ptype='p', rule=['bob', 'data2', 'write'])
68+
adapter.add_policy(sec=None, ptype='p', rule=['data2_admin', 'data2', 'read'])
69+
adapter.add_policy(sec=None, ptype='p', rule=['data2_admin', 'data2', 'write'])
70+
adapter.add_policy(sec=None, ptype='g', rule=['alice', 'data2_admin'])
71+
72+
e.load_policy()
73+
74+
self.assertFalse(e.enforce('alice', 'data1', 'write'))
75+
self.assertFalse(e.enforce('bob', 'data1', 'read'))
76+
self.assertTrue(e.enforce('bob', 'data2', 'write'))
77+
self.assertTrue(e.enforce('alice', 'data2', 'read'))
78+
self.assertTrue(e.enforce('alice', 'data2', 'write'))
79+
self.assertFalse(e.enforce('bogus', 'data2', 'write'))
80+
81+
def test_save_policy(self):
82+
'''
83+
test save_policy
84+
'''
85+
model = casbin.Enforcer(get_fixture('rbac_model.conf'), get_fixture('rbac_policy.csv')).model
86+
adapter = Adapter('mongodb://localhost:27017', 'casbin_test')
87+
adapter.save_policy(model)
88+
e = casbin.Enforcer(get_fixture('rbac_model.conf'), adapter)
89+
90+
self.assertFalse(e.enforce('alice', 'data1', 'read'))
91+
self.assertFalse(e.enforce('bob', 'data1', 'read'))
92+
self.assertTrue(e.enforce('bob', 'data2', 'write'))
93+
self.assertTrue(e.enforce('alice', 'data2', 'read'))
94+
self.assertTrue(e.enforce('alice', 'data2', 'write'))
95+
96+
def test_str(self):
97+
'''
98+
test __str__ function
99+
'''
100+
rule = CasbinRule(ptype='p', v0='alice', v1='data1', v2='read')
101+
self.assertEqual(str(rule), 'p, alice, data1, read')
102+
103+
def test_repr(self):
104+
'''
105+
test __repr__ function
106+
'''
107+
adapter = Adapter('mongodb://localhost:27017', 'casbin_test')
108+
rule = CasbinRule(ptype='p', v0='alice', v1='data1', v2='read')
109+
self.assertEqual(repr(rule), '<CasbinRule :"p, alice, data1, read">')
110+
adapter.save_policy(rule)
111+
self.assertRegex(repr(rule), r'<CasbinRule :"p, alice, data1, read">')

0 commit comments

Comments
 (0)