Skip to content

Commit 2c53d3c

Browse files
Moving board_deparse to boards.py (#247)
* Moving board_deparse to boards.py * Pass doctest
1 parent 0aefeea commit 2c53d3c

File tree

3 files changed

+65
-66
lines changed

3 files changed

+65
-66
lines changed

pins/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@
1111
# Imports ----
1212
from .cache import cache_prune, cache_info
1313
from .constructors import (
14-
board_deparse,
1514
board_folder,
1615
board_temp,
1716
board_local,
@@ -25,3 +24,4 @@
2524
board_gcs,
2625
board,
2726
)
27+
from .boards import board_deparse

pins/boards.py

Lines changed: 60 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -753,6 +753,66 @@ def _touch_cache(self, path):
753753
return touch_access_time(path_to_hashed)
754754

755755

756+
def board_deparse(board: BaseBoard):
757+
"""Return a representation of how a board could be reconstructed.
758+
759+
Note that this function does not try to represent the exact arguments used
760+
to construct a board, but key pieces (like the path to the board). You may
761+
need to specify environment variables with API keys to complete the connection.
762+
763+
Parameters
764+
----------
765+
board:
766+
A pins board to be represented.
767+
768+
Examples
769+
--------
770+
771+
The example below deparses a board connected to Posit Connect.
772+
773+
>>> from pins.constructors import board_connect
774+
>>> board_deparse(board_connect(server_url="http://example.com", api_key="xxx"))
775+
"board_connect(server_url='http://example.com')"
776+
777+
Note that the deparsing a Posit Connect board does not keep the api_key,
778+
which is sensitive information. In this case, you can set the CONNECT_API_KEY
779+
environment variable to connect.
780+
781+
Below is an example of representing a board connected to a local folder.
782+
783+
>>> from pins.constructors import board_folder
784+
>>> board_deparse(board_folder("a/b/c"))
785+
"board_folder('a/b/c')"
786+
787+
>>> board_deparse(board_folder(path="a/b/c", allow_pickle_read=True))
788+
"board_folder('a/b/c', allow_pickle_read=True)"
789+
"""
790+
if board.allow_pickle_read is not None:
791+
allow_pickle = f", allow_pickle_read={repr(board.allow_pickle_read)}"
792+
else:
793+
allow_pickle = ""
794+
795+
prot = board.fs.protocol
796+
797+
if prot == "rsc":
798+
url = board.fs.api.server_url
799+
return f"board_connect(server_url={repr(url)}{allow_pickle})"
800+
elif prot in ["file", ("file", "local")]:
801+
return f"board_folder({repr(board.board)}{allow_pickle})"
802+
elif set(prot) == {"s3", "s3a"}:
803+
return f"board_s3({repr(board.board)}{allow_pickle})"
804+
elif prot == "abfs":
805+
return f"board_azure({repr(board.board)}{allow_pickle})"
806+
elif set(prot) == {"gcs", "gs"} or prot == "gs":
807+
return f"board_gcs({repr(board.board)}{allow_pickle})"
808+
elif prot == "http":
809+
return f"board_url({repr(board.board)}, {board.pin_paths}{allow_pickle})"
810+
else:
811+
raise NotImplementedError(
812+
f"board deparsing currently not supported for protocol: {prot}"
813+
)
814+
815+
756816
class BoardManual(BaseBoard):
757817
"""Simple board that accepts a dictionary of form `pin_name: path`.
758818
@@ -1089,9 +1149,6 @@ def user_name(self):
10891149
return self._user_name
10901150

10911151
def prepare_pin_version(self, pin_dir_path, x, name: "str | None", *args, **kwargs):
1092-
# TODO: should move board_deparse into utils, to avoid circular import
1093-
from .constructors import board_deparse
1094-
10951152
# RSC pin names can have form <user_name>/<name>, but this will try to
10961153
# create the object in a directory named <user_name>. So we grab just
10971154
# the <name> part.

pins/constructors.py

Lines changed: 4 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -2,76 +2,18 @@
22
import os
33
import tempfile
44

5-
from .boards import BaseBoard, BoardRsConnect, BoardManual
5+
from .boards import BaseBoard, BoardRsConnect, BoardManual, board_deparse
66
from .cache import PinsCache, PinsRscCacheMapper, PinsAccessTimeCache, prefix_cache
77
from .config import get_data_dir, get_cache_dir
88

9+
# Kept here for backward-compatibility reasons.
10+
board_deparse # Note that this is not a constructor, but a function to represent them.
11+
912

1013
class DEFAULT:
1114
pass
1215

1316

14-
# Representing constructors ===================================================
15-
16-
# Note that this is not a constructor, but a function to represent them.
17-
def board_deparse(board: BaseBoard):
18-
"""Return a representation of how a board could be reconstructed.
19-
20-
Note that this function does not try to represent the exact arguments used
21-
to construct a board, but key pieces (like the path to the board). You may
22-
need to specify environment variables with API keys to complete the connection.
23-
24-
Parameters
25-
----------
26-
board:
27-
A pins board to be represented.
28-
29-
Examples
30-
--------
31-
32-
The example below deparses a board connected to Posit Connect.
33-
34-
>>> board_deparse(board_connect(server_url="http://example.com", api_key="xxx"))
35-
"board_connect(server_url='http://example.com')"
36-
37-
Note that the deparsing a Posit Connect board does not keep the api_key,
38-
which is sensitive information. In this case, you can set the CONNECT_API_KEY
39-
environment variable to connect.
40-
41-
Below is an example of representing a board connected to a local folder.
42-
43-
>>> board_deparse(board_folder("a/b/c"))
44-
"board_folder('a/b/c')"
45-
46-
>>> board_deparse(board_folder(path="a/b/c", allow_pickle_read=True))
47-
"board_folder('a/b/c', allow_pickle_read=True)"
48-
"""
49-
if board.allow_pickle_read is not None:
50-
allow_pickle = f", allow_pickle_read={repr(board.allow_pickle_read)}"
51-
else:
52-
allow_pickle = ""
53-
54-
prot = board.fs.protocol
55-
56-
if prot == "rsc":
57-
url = board.fs.api.server_url
58-
return f"board_connect(server_url={repr(url)}{allow_pickle})"
59-
elif prot in ["file", ("file", "local")]:
60-
return f"board_folder({repr(board.board)}{allow_pickle})"
61-
elif set(prot) == {"s3", "s3a"}:
62-
return f"board_s3({repr(board.board)}{allow_pickle})"
63-
elif prot == "abfs":
64-
return f"board_azure({repr(board.board)}{allow_pickle})"
65-
elif set(prot) == {"gcs", "gs"} or prot == "gs":
66-
return f"board_gcs({repr(board.board)}{allow_pickle})"
67-
elif prot == "http":
68-
return f"board_url({repr(board.board)}, {board.pin_paths}{allow_pickle})"
69-
else:
70-
raise NotImplementedError(
71-
f"board deparsing currently not supported for protocol: {prot}"
72-
)
73-
74-
7517
# Board constructors ==========================================================
7618
# note that libraries not used by board classes above are imported within these
7719
# functions. may be worth moving these funcs into their own module.

0 commit comments

Comments
 (0)