Skip to content
This repository has been archived by the owner on Sep 12, 2024. It is now read-only.

(PR-SERIES-P6) [ENHANCEMENT]: Implement Access Validation #583

Merged
merged 6 commits into from
Aug 31, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 8 additions & 4 deletions jaclang/cli/cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -251,6 +251,8 @@ def enter(
base = base if base else "./"
mod = mod[:-4]

jctx = ExecutionContext.create(session=session, root=root)

if filename.endswith(".jac"):
ret_module = jac_import(
target=mod,
Expand All @@ -270,19 +272,21 @@ def enter(
override_name="__main__" if main else None,
)
else:
jctx.close()
JacMachine.detach()
raise ValueError("Not a valid file!\nOnly supports `.jac` and `.jir`")

jctx = ExecutionContext.create(session=session, root=root, entry=node)

if ret_module:
(loaded_mod,) = ret_module
if not loaded_mod:
print("Errors occurred while importing the module.")
else:
architype = getattr(loaded_mod, entrypoint)(*args)
if isinstance(architype, WalkerArchitype):
Jac.spawn_call(jctx.entry.architype, architype)

jctx.set_entry_node(node)

if isinstance(architype, WalkerArchitype) and jctx.validate_access():
Jac.spawn_call(jctx.entry_node.architype, architype)

jctx.close()
JacMachine.detach()
Expand Down
18 changes: 16 additions & 2 deletions jaclang/plugin/default.py
Original file line number Diff line number Diff line change
Expand Up @@ -459,9 +459,16 @@ def connect(
left = [left] if isinstance(left, NodeArchitype) else left
right = [right] if isinstance(right, NodeArchitype) else right
edges = []

root = Jac.get_root().__jac__

for i in left:
for j in right:
edges.append(edge_spec(i.__jac__, j.__jac__))
_left = i.__jac__
if root.has_connect_access(_left):
for j in right:
_right = j.__jac__
if root.has_connect_access(_right):
edges.append(edge_spec(_left, _right))
return right if not edges_only else edges

@staticmethod
Expand All @@ -476,25 +483,32 @@ def disconnect(
disconnect_occurred = False
left = [left] if isinstance(left, NodeArchitype) else left
right = [right] if isinstance(right, NodeArchitype) else right

root = Jac.get_root().__jac__

for i in left:
node = i.__jac__
for anchor in set(node.edges):
if (
(source := anchor.source)
and (target := anchor.target)
and (not filter_func or filter_func([anchor.architype]))
and source.architype
and target.architype
ypkang marked this conversation as resolved.
Show resolved Hide resolved
):
if (
dir in [EdgeDir.OUT, EdgeDir.ANY]
and node == source
and target.architype in right
and root.has_write_access(target)
):
anchor.destroy() if anchor.persistent else anchor.detach()
disconnect_occurred = True
if (
dir in [EdgeDir.IN, EdgeDir.ANY]
and node == target
and source.architype in right
and root.has_write_access(source)
):
anchor.destroy() if anchor.persistent else anchor.detach()
disconnect_occurred = True
Expand Down
82 changes: 82 additions & 0 deletions jaclang/plugin/tests/fixtures/other_root_access.jac
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
import:py from jaclang.runtimelib.architype {Anchor}
import:py from uuid {UUID}

node A {
has val: int;
}

walker check_node {
can enter with `root entry {
visit [-->];
}

can enter2 with A entry {
print(here);
}
}

walker update_node {
has val: int;

can enter2 with A entry {
here.val = self.val;
}
}

walker create_node {
has val: int;

can enter with `root entry {
a = A(val=self.val);
here ++> a;
print(a.__jac__.id);
}
}

walker create_other_root {
can enter with `root entry {
other_root = `root().__jac__;
other_root.save();
print(other_root.id);
}
}

walker allow_other_root_access {
has root_id: str, level: int | str = 1, via_all: bool = False;

can enter_root with `root entry {
if self.via_all {
here.__jac__.unrestrict(self.level);
} else {
here.__jac__.allow_root(UUID(self.root_id), self.level);
}
}

can enter_nested with A entry {
if self.via_all {
here.__jac__.unrestrict(self.level);
} else {
here.__jac__.allow_root(UUID(self.root_id), self.level);
}
}
}

walker disallow_other_root_access {
has root_id: str, via_all: bool = False;

can enter_root with `root entry {
if self.via_all {
here.__jac__.restrict();
} else {
here.__jac__.disallow_root(UUID(self.root_id));
}
}

can enter_nested with A entry {
if self.via_all {
here.__jac__.restrict();
} else {
here.__jac__.disallow_root(UUID(self.root_id));
}
}
}
Loading
Loading