99from kbcstorage .base import Endpoint
1010from kbcstorage .files import Files
1111from kbcstorage .jobs import Jobs
12+ from typing import List # the legacy Workspaces class below unfortunately defines its own method called list
1213
1314
14- def _make_body (mapping , source_key = 'source' ):
15+ def _make_body (mapping , source_key = 'source' , preserve : bool = True ):
1516 """
1617 Given a dict mapping Keboola tables to aliases, construct the body of
1718 the HTTP request to load said tables.
@@ -21,7 +22,7 @@ def _make_body(mapping, source_key='source'):
2122 be loaded (ie. 'in.c-bucker.table_name') and values contain the
2223 aliases to which they will be loaded (ie. 'table_name').
2324 """
24- body = {}
25+ body = {'preserve' : str ( preserve ). lower () }
2526 template = 'input[{0}][{1}]'
2627 for i , (k , v ) in enumerate (mapping .items ()):
2728 body [template .format (i , source_key )] = k
@@ -72,7 +73,7 @@ def detail(self, workspace_id):
7273 url = '{}/{}' .format (self .base_url , workspace_id )
7374 return self ._get (url )
7475
75- def create (self , backend = None , timeout = None ):
76+ def create (self , backend = None , timeout = None , login_type = None , public_key = None , read_all_objects = False ):
7677 """
7778 Create a new Workspace and return the credentials.
7879
@@ -87,7 +88,10 @@ def create(self, backend=None, timeout=None):
8788 """
8889 body = {
8990 'backend' : backend ,
90- 'statementTimeoutSeconds' : timeout
91+ 'statementTimeoutSeconds' : timeout ,
92+ 'loginType' : login_type ,
93+ 'publicKey' : public_key ,
94+ 'readOnlyStorageAccess' : str (read_all_objects ).lower () # convert bool to lowercase true or false
9195 }
9296
9397 return self ._post (self .base_url , data = body )
@@ -122,29 +126,50 @@ def reset_password(self, workspace_id):
122126 url = '{}/{}/password' .format (self .base_url , workspace_id )
123127 return self ._post (url )
124128
125- def load_tables (self , workspace_id , table_mapping , preserve = None ):
129+ def set_public_key (self , workspace_id , public_key ):
130+ """
131+ Set the public key for the workspace.
132+ """
133+ data = {
134+ 'publicKey' : public_key
135+ }
136+ url = '{}/{}/public-key' .format (self .base_url , workspace_id )
137+ return self ._post (url , json = data )
138+
139+ def load_tables (self , workspace_id : int | str , table_mapping : dict | List [dict ], preserve = True , load_type = 'load' ):
126140 """
127141 Load tabes from storage into a workspace.
128142
129143 Args:
130144 workspace_id (int or str): The id of the workspace to which to load
131145 the tables.
132- table_mapping (:obj:`dict`): Source table names mapped to
133- destination table names.
146+ table_mapping (:obj:`dict` or :obj:`list` ): Source table names mapped to
147+ destination table names. or a list of dicts with detailed tables specification.
134148 preserve (bool): If False, drop tables, else keep tables in
135149 workspace.
150+ load_type (str): Type of load, either 'load' or 'load-clone'. Defaults to 'load'.
136151
137152 Raises:
138153 requests.HTTPError: If the API request fails.
139154
140155 Todo:
141156 * Column data types.
142157 """
143- body = _make_body (table_mapping )
144- body ['preserve' ] = preserve
145- url = '{}/{}/load' .format (self .base_url , workspace_id )
158+ load_type = load_type .lower ()
159+ if load_type not in ['load' , 'load-clone' ]:
160+ raise ValueError ("Invalid load_type: {}, supports only load and load-clone" .format (load_type ))
161+
162+ url = "/" .join ([self .base_url , str (workspace_id ), load_type ])
163+
164+ req = None
165+ if isinstance (table_mapping , dict ):
166+ body = _make_body (table_mapping , preserve = preserve )
167+ req = self ._post (url , data = body )
168+ elif isinstance (table_mapping , list ):
169+ body = {'input' : table_mapping , 'preserve' : str (preserve ).lower ()}
170+ req = self ._post (url , json = body )
146171
147- return self . _post ( url , data = body )
172+ return req
148173
149174 def load_files (self , workspace_id , file_mapping ):
150175 """
0 commit comments