1+ from multiprocessing .sharedctypes import Value
12from .LoopProjectFile import Get , Set , CreateBasic , OpenProjectFile , CheckFileValid ,CheckFileIsLoopProjectFile
23from .LoopProjectFileUtils import ElementToDataframe , ElementFromDataframe
34import LoopProjectFile
@@ -77,18 +78,45 @@ def new(cls, filename):
7778 projectfile = ProjectFile (filename )
7879 return projectfile
7980
80- def is_valid (self ):
81+ @property
82+ def valid (self ) -> bool :
83+ """Check if the project file is valid
84+
85+ Returns
86+ -------
87+ bool
88+ true if project file is valid, false if not
89+ """
90+ return self .is_valid ()
91+
92+ def is_valid (self ) -> bool :
8193 return CheckFileValid (self .project_filename )
8294
8395 def _add_names_to_df (self , log , df ):
96+ """_summary_
97+
98+ Parameters
99+ ----------
100+ log : _type_
101+ _description_
102+ df : _type_
103+ _description_
104+ """
84105 df ['name' ] = 'none'
85106 for stratigraphic_id in log .index :
86107 df .loc [df ['layerId' ] == stratigraphic_id ,'name' ] = \
87108 log .loc [stratigraphic_id ,'name' ]
88109
89110
90111 @property
91- def extents (self ):
112+ def extents (self )-> np .ndarray :
113+ """Get the extents of the model
114+
115+ Returns
116+ -------
117+ np.ndarray
118+ _description_
119+ """
92120 resp = Get (self .project_filename ,'extents' )
93121 if resp ['errorFlag' ] == True :
94122 return None
@@ -101,128 +129,180 @@ def extents(self,extents):
101129
102130
103131 @property
104- def version (self ):
132+ def version (self ) -> str :
133+ """Get version of the project file
134+
135+ Returns
136+ -------
137+ str
138+ version string major.minor.patch
139+ """
105140 resp = Get (self .project_filename ,'version' )
106141 if resp ['errorFlag' ] == True :
107142 return None
108143 return "{}.{}.{}" .format (* resp ['value' ])
109144
110145 @property
111- def origin (self ):
146+ def origin (self ) -> np .ndarray :
147+ """Get the origin of the model"""
112148 origin = np .zeros (3 )
113149 origin [0 ] = self .extents ['utm' ][2 ]
114150 origin [1 ] = self .extents ['utm' ][4 ]
115151 origin [2 ] = self .extents ['depth' ][0 ]
116152 return origin
117153 @property
118- def maximum (self ):
154+ def maximum (self ) -> np .ndarray :
155+ """Get top right hand coordinate of the bouinding box
156+
157+ Returns
158+ -------
159+ np.ndarray
160+ _description_
161+ """
119162 maximum = np .zeros (3 )
120163 maximum [0 ] = self .extents ['utm' ][3 ]
121164 maximum [1 ] = self .extents ['utm' ][5 ]
122165 maximum [2 ] = self .extents ['depth' ][1 ]
123166 return maximum
124- # should we be able to set the version or should this be fixed?
125- # @version.setter
126- # def version(self, version):
127- # if isinstance(version, str):
128- # version = version.split('.')
129- # if len(version) != 3:
130- # raise ValueError('Version must be in the format major.minor.patch')
131- # version = list(map(int, version))
132- # resp = Set(self.project_filename,'version',version=version)
133- # if resp['errorFlag'] == True:
134- # raise ValueError('Version must be in the format major.minor.patch')
167+
135168
136169 @property
137- def faultObservations (self ):
170+ def faultObservations (self ) -> pd . DataFrame :
138171 return self .__getitem__ ('faultObservations' )
139172
140173 @faultObservations .setter
141- def faultObservations (self , value ):
174+ def faultObservations (self , value :pd .DataFrame ):
175+ if isinstance (value , pd .DataFrame ):
176+ self .__setitem__ ('faultObservations' , value )
177+ self ._validate_data_frame_columns (value , [ 'eventId' , 'easting' , 'northing' , 'altitude' ,'type' ,'dipDir' ,'dip' , 'dipPolarity' , 'val' , 'displacement' ,'posOnly' ])
142178 self .__setitem__ ('faultObservations' , value )
143179
144180
145181 @property
146- def faultLocations (self ):
182+ def faultLocations (self )-> pd .DataFrame :
183+ """Get only the observations of the fault location
184+
185+ Returns
186+ -------
187+ pd.DataFrame
188+ _description_
189+ """
147190 df = self .__getitem__ ('faultObservations' )
148191 # self._add_names_to_df(self.faultLog,df)
149192 return df .loc [df ['posOnly' ]== 1 ,:]
150193
194+ def _validate_data_frame_columns (self , df :pd .DataFrame , columns :list ):
195+ for c in columns .keys ():
196+ if c in df .columns :
197+ columns [c ] = True
198+ columns_in_df = True
199+ for c in columns .keys ():
200+ if columns [c ] == False :
201+ columns_in_df = False
202+ print (f'Column: { c } not dataframe' )
203+ # logger.error(f'Column: {c} not dataframe')
204+ if columns_in_df == False :
205+ raise ValueError ('Columns not in dataframe' )
151206 @faultLocations .setter
152- def faultLocations (self , value ):
207+ def faultLocations (self , value :pd .DataFrame ):
208+ """Update the faultObservations with new fault locations
209+
210+ Parameters
211+ ----------
212+ value : pd.DataFrame
213+ _description_
214+ """
215+ if isinstance (value , pd .DataFrame ) == False :
216+ raise TypeError ('faultLocations must be set with a pandas dataframe' )
217+ columns = {'eventId' :False , 'easting' :False , 'northing' :False , 'altitude' :False , 'val' :False }
218+ self ._validate_data_frame_columns (value , columns )
153219 df = self .__getitem__ ('faultObservations' )
154- value = pd .concat ([value ,df .loc [df ['posOnly' ]== 1 ,:]])
220+ value ['posOnly' ] == 1
221+ value = pd .concat ([value ,df .loc [df ['posOnly' ]== 0 ,:]])
155222 value .reset_index (inplace = True )
156223 self .__setitem__ ('faultObservations' , value )
157224
158225
159226 @property
160- def faultOrientations (self ):
227+ def faultOrientations (self )-> pd . DataFrame :
161228 df = self .__getitem__ ('faultObservations' )
162229 return df .loc [df ['posOnly' ]== 0 ,:]
163230
164231 @faultOrientations .setter
165- def faultOrientations (self , value ):
232+ def faultOrientations (self , value :pd .DataFrame ):
233+ if isinstance (value , pd .DataFrame ) == False :
234+ raise TypeError ('faultOrientations must be set with a pandas dataframe' )
235+ columns = {'eventId' :False , 'easting' :False , 'northing' :False , 'altitude' :False , 'dipDir' :False , 'dip' :False , 'dipPolarity' :False }
236+ self ._validate_data_frame_columns (value , columns )
237+
166238 df = self .__getitem__ ('faultObservations' )
167- value = pd .concat ([value ,df .loc [df ['posOnly' ]== 0 ,:]])
239+ value ['posOnly' ] == 0
240+ value = pd .concat ([value ,df .loc [df ['posOnly' ]== 1 ,:]])
168241 value .reset_index (inplace = True )
169242 self .__setitem__ ('faultObservations' , value )
170243
171244
172245 @property
173- def faultLog (self ):
246+ def faultLog (self )-> pd . DataFrame :
174247 return self .__getitem__ ('faultLog' ).set_index ('name' )
175248
176249 @faultLog .setter
177- def faultLog (self , value ):
250+ def faultLog (self , value : pd . DataFrame ):
178251 self .__setitem__ ('faultLog' ,value )
179252
180253
181254 @property
182- def foliationObservations (self ):
255+ def foliationObservations (self )-> pd . DataFrame :
183256 return self .__getitem__ ('foliationObservations' )
184257
185258 @foliationObservations .setter
186- def foliationObservations (self , value ):
259+ def foliationObservations (self , value : pd . DataFrame ):
187260 self .__setitem__ ('foliationObservations' ,value )
188261
189262
190263 @property
191- def foldObservations (self ):
264+ def foldObservations (self )-> pd . DataFrame :
192265 return self .__getitem__ ('foldObservations' )
193266
194267 @foldObservations .setter
195- def foldObservations (self , value ):
268+ def foldObservations (self , value : pd . DataFrame ):
196269 self .__setitem__ ('foldObservations' , value )
197270
198271
199272 @property
200- def stratigraphicLog (self ):
273+ def stratigraphicLog (self )-> pd . DataFrame :
201274 return self .__getitem__ ('stratigraphicLog' )
202275
203276 @stratigraphicLog .setter
204- def stratigraphicLog (self , value ):
277+ def stratigraphicLog (self , value :pd .DataFrame ):
278+ ## TODO add a validator
205279 self .__setitem__ ('stratigraphicLog' , value )
206280
207281
208282 @property
209- def stratigraphyLocations (self ):
283+ def stratigraphyLocations (self )-> pd . DataFrame :
210284 df = self .__getitem__ ('contacts' )
211285 self ._add_names_to_df (self .stratigraphicLog ,df )
212286 return df
213287
214288 @stratigraphyLocations .setter
215- def stratigraphyLocations (self , value ):
289+ def stratigraphyLocations (self , value :pd .DataFrame ):
290+ if isinstance (value , pd .DataFrame ) == False :
291+ raise TypeError ('stratigraphyLocations must be set with a pandas dataframe' )
292+ self ._validate_data_frame_columns (value , ['layerId' ,'easting' ,'northing' ,'altitude' , 'type' , 'name' ])
216293 self .__setitem__ ('contacts' ,value )
217294
218295 @property
219- def stratigraphyOrientations (self ):
296+ def stratigraphyOrientations (self )-> pd . DataFrame :
220297 df = self .__getitem__ ('stratigraphicObservations' )
221298 self ._add_names_to_df (self .stratigraphicLog ,df )
222299 return df
223300
224301 @stratigraphyOrientations .setter
225- def stratigraphyOrientations (self , value ):
302+ def stratigraphyOrientations (self , value :pd .DataFrame ):
303+ if isinstance (value , pd .DataFrame ) == False :
304+ raise TypeError ('stratigraphyOrientations must be set with a pandas dataframe' )
305+ self ._validate_data_frame_columns (value , ['layerId' ,'easting' ,'northing' ,'altitude' ,'type' , 'name' ,'dipDir' ,'dip' ,'dipPolarity' ,'layer' ])
226306 self .__setitem__ ('stratigraphicObservations' ,value )
227307
228308
@@ -237,6 +317,12 @@ def __getitem__(self, element):
237317 else :
238318 return LoopProjectFile .ElementToDataframe (self .project_filename ,
239319 element ,compoundTypeMap [element ])
320+ # if the project file is empty for a given element, return an empty dataframe with the correct headers
321+ if resp ['errorFlag' ] == True :
322+ if resp ['errorString' ] == 'No Observations present in DataCollection for access request' :
323+ ## this isn't really ideal and maybe need to be removed but at least it gives an idea of the column
324+ ## names needed.
325+ return pd .DataFrame (columns = list (compoundTypeMap [element ].names ))
240326 # return ProjectFileElement(self.project_filename, element).value
241327
242328 def __setitem__ (self , element , value ):
0 commit comments