Skip to content

Commit 0c94f30

Browse files
committed
feat: rsconnect fs access_type args
1 parent 0cc265e commit 0c94f30

File tree

3 files changed

+45
-5
lines changed

3 files changed

+45
-5
lines changed

pins/rsconnect/api.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -304,7 +304,7 @@ def get_content_item(self, guid: str) -> Content:
304304
return Content(result)
305305

306306
def post_content_item(
307-
self, name, access_type, title: str = "", description: str = "", **kwargs
307+
self, name, access_type: str, title: str = "", description: str = "", **kwargs
308308
) -> Content:
309309
data = self._get_params(locals(), exclude={"kwargs"})
310310
result = self.query_v1("content", "POST", json={**data, **kwargs})

pins/rsconnect/fs.py

Lines changed: 25 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,17 @@
1818
RSC_CODE_OBJECT_DOES_NOT_EXIST,
1919
)
2020

21+
# Misc ----
22+
23+
24+
def _not_impl_args_kwargs(args, kwargs):
25+
return NotImplementedError(
26+
"Additional args and kwargs not supported." f"\nArgs: {args}\nKwargs: {kwargs}"
27+
)
28+
29+
30+
# Bundles ----
31+
2132

2233
@dataclass
2334
class PinBundleManifestMetadata:
@@ -148,6 +159,7 @@ def put(
148159
rpath,
149160
recursive=False,
150161
*args,
162+
access_type="acl",
151163
deploy=True,
152164
cls_manifest=PinBundleManifest,
153165
**kwargs,
@@ -160,6 +172,8 @@ def put(
160172
A path to the local bundle directory.
161173
rpath: str
162174
A path to the content where the bundle is being put.
175+
access_type:
176+
Who can use and view this content? Must be one of all, logged_in or acl.
163177
cls_manifest:
164178
If maniest does not exist, a class with an .add_manifest_to_directory()
165179
method.
@@ -168,6 +182,9 @@ def put(
168182

169183
parsed = self.parse_path(rpath)
170184

185+
if len(args) or len(kwargs):
186+
raise _not_impl_args_kwargs(args, kwargs)
187+
171188
if recursive is False:
172189
raise NotImplementedError(
173190
"Must set recursive to True in order to put any RSConnect content."
@@ -185,7 +202,7 @@ def put(
185202
# TODO: this could be seen as analogous to mkdir (which gets
186203
# called by pins anyway)
187204
# TODO: hard-coded acl bad?
188-
content = self.api.post_content_item(parsed.content, "acl")
205+
content = self.api.post_content_item(parsed.content, access_type)
189206

190207
# Create bundle (with manifest.json inserted if missing) ----
191208

@@ -265,18 +282,22 @@ def exists(self, path: str, **kwargs) -> bool:
265282
except RsConnectApiMissingContentError:
266283
return False
267284

268-
def mkdir(self, path, create_parents=True, **kwargs) -> None:
285+
def mkdir(
286+
self, path, create_parents=True, *args, access_type="acl", **kwargs
287+
) -> None:
269288
parsed = self.parse_path(path)
270289

290+
if len(args) or len(kwargs):
291+
raise _not_impl_args_kwargs(args, kwargs)
292+
271293
if not isinstance(parsed, ContentPath):
272294
raise ValueError(f"Requires path to content, but received: {path}")
273295

274296
if self.exists(path):
275297
raise FileExistsError(path)
276298

277299
# TODO: could implement and call makedirs, but seems overkill
278-
# TODO: hard-coded "acl"?
279-
self.api.post_content_item(parsed.content, "acl", **kwargs)
300+
self.api.post_content_item(parsed.content, access_type, **kwargs)
280301

281302
def info(self, path, **kwargs) -> "User | Content | Bundle":
282303
# TODO: source of fsspec info uses self._parent to check cache?

pins/tests/test_rsconnect_api.py

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -426,6 +426,25 @@ def test_rsconnect_fs_put_bundle(fs_short):
426426
assert f_index.read().decode() == (Path(path_to_example) / "index.html").read_text()
427427

428428

429+
def test_rsconnect_fs_put_bundle_all_access(fs_short):
430+
import requests
431+
432+
# TODO: use pkg_resources to get this
433+
path_to_example = "pins/tests/example-bundle"
434+
fs_short.put(
435+
path_to_example, "susan/test-content", recursive=True, access_type="all"
436+
)
437+
438+
# access control is set at the content (not bundle) level. we need to get the
439+
# content guid to recreate the "shareable" link
440+
content = fs_short.info("susan/test-content")
441+
442+
r = requests.get(f"{fs_short.api.server_url}/content/{content['guid']}")
443+
r.raise_for_status()
444+
445+
assert r.text == (Path(path_to_example) / "index.html").read_text()
446+
447+
429448
# fs.mkdir ----
430449

431450

0 commit comments

Comments
 (0)