1414
1515import pandas as pd
1616import petab .v1 as petab
17+ from petab import v2
1718
1819try :
1920 import roadrunner
3940from ..startpoint import StartpointMethod
4041from .objective_creator import (
4142 AmiciObjectiveCreator ,
43+ AmiciPetabV2ObjectiveCreator ,
4244 ObjectiveCreator ,
4345 PetabSimulatorObjectiveCreator ,
4446 RoadRunnerObjectiveCreator ,
@@ -70,7 +72,7 @@ class PetabImporter:
7072
7173 def __init__ (
7274 self ,
73- petab_problem : petab .Problem ,
75+ petab_problem : petab .Problem | v2 . Problem ,
7476 output_folder : str | None = None ,
7577 model_name : str | None = None ,
7678 validate_petab : bool = True ,
@@ -149,8 +151,18 @@ def __init__(
149151
150152 self .validate_petab = validate_petab
151153 if self .validate_petab :
152- if petab .lint_problem (petab_problem ):
154+ if isinstance (petab_problem , petab .Problem ) and petab .lint_problem (
155+ petab_problem
156+ ):
153157 raise ValueError ("Invalid PEtab problem." )
158+ if (
159+ isinstance (petab_problem , v2 .Problem )
160+ and (
161+ validation_result := petab_problem .validate ()
162+ ).has_errors ()
163+ ):
164+ validation_result .log (logger = logger )
165+ raise ValueError ("Invalid PEtab v2 problem." )
154166 if self ._hierarchical and validate_petab_hierarchical :
155167 from ..hierarchical .petab import (
156168 validate_hierarchical_petab_problem ,
@@ -186,7 +198,15 @@ def from_yaml(
186198 simulator_type : str = AMICI ,
187199 ) -> PetabImporter :
188200 """Simplified constructor using a petab yaml file."""
189- petab_problem = petab .Problem .from_yaml (yaml_config )
201+ from petab .versions import get_major_version
202+
203+ match get_major_version (yaml_config ):
204+ case 1 :
205+ petab_problem = petab .Problem .from_yaml (yaml_config )
206+ case 2 :
207+ petab_problem = v2 .Problem .from_yaml (yaml_config )
208+ case _:
209+ raise ValueError ("Only PEtab v1 and v2 are supported." )
190210
191211 return PetabImporter (
192212 petab_problem = petab_problem ,
@@ -278,6 +298,42 @@ def create_prior(self) -> NegLogParameterPriors | None:
278298 else :
279299 return None
280300
301+ def _create_prior_v2 (self ) -> NegLogParameterPriors | None :
302+ """Create prior for PEtab v2 problem."""
303+ import petab .v2 .C as petab_c
304+
305+ import pypesto .C as pypesto_c
306+
307+ petab_to_pypesto = {
308+ petab_c .LAPLACE : pypesto_c .LAPLACE ,
309+ petab_c .LOG_LAPLACE : pypesto_c .LOG_LAPLACE ,
310+ petab_c .LOG_NORMAL : pypesto_c .LOG_NORMAL ,
311+ petab_c .LOG_UNIFORM : pypesto_c .LOG_UNIFORM ,
312+ petab_c .NORMAL : pypesto_c .NORMAL ,
313+ petab_c .UNIFORM : pypesto_c .UNIFORM ,
314+ }
315+
316+ prior_list = []
317+ for parameter in self .petab_problem .parameters :
318+ if not parameter .estimate or parameter .prior_distribution is None :
319+ continue
320+
321+ prior_list .append (
322+ get_parameter_prior_dict (
323+ index = len (prior_list ),
324+ # TODO map names
325+ prior_type = petab_to_pypesto .get (
326+ str (parameter .prior_distribution ),
327+ str (parameter .prior_distribution ),
328+ ),
329+ prior_parameters = parameter .prior_parameters ,
330+ parameter_scale = "lin" ,
331+ )
332+ )
333+ if prior_list :
334+ return NegLogParameterPriors (prior_list )
335+ return None
336+
281337 def create_startpoint_method (self , ** kwargs ) -> StartpointMethod :
282338 """Create a startpoint method.
283339
@@ -307,6 +363,22 @@ def create_objective_creator(
307363 has to be provided. Otherwise the argument is not used.
308364
309365 """
366+ if isinstance (self .petab_problem , v2 .Problem ):
367+ if simulator_type != AMICI :
368+ raise ValueError (
369+ "Only 'amici' simulator type is supported for PEtab v2 "
370+ "problems."
371+ )
372+ return AmiciPetabV2ObjectiveCreator (
373+ petab_problem = self .petab_problem ,
374+ output_folder = self .output_folder ,
375+ model_name = self .model_name ,
376+ hierarchical = self ._hierarchical ,
377+ inner_options = self .inner_options ,
378+ non_quantitative_data_types = self ._non_quantitative_data_types ,
379+ validate_petab = self .validate_petab ,
380+ )
381+
310382 if simulator_type == AMICI :
311383 return AmiciObjectiveCreator (
312384 petab_problem = self .petab_problem ,
@@ -365,10 +437,26 @@ def create_problem(
365437 objective = self .objective_constructor .create_objective (** kwargs )
366438
367439 x_fixed_indices = self .petab_problem .x_fixed_indices
368- x_fixed_vals = self .petab_problem .x_nominal_fixed_scaled
369440 x_ids = self .petab_problem .x_ids
370- lb = self .petab_problem .lb_scaled
371- ub = self .petab_problem .ub_scaled
441+ if isinstance (self .petab_problem , petab .Problem ):
442+ # PEtab v1
443+ x_fixed_vals = self .petab_problem .x_nominal_fixed_scaled
444+ lb = self .petab_problem .lb_scaled
445+ ub = self .petab_problem .ub_scaled
446+ x_scales = [
447+ self .petab_problem .parameter_df .loc [
448+ x_id , petab .PARAMETER_SCALE
449+ ]
450+ for x_id in x_ids
451+ ]
452+ prior = self .create_prior ()
453+ else :
454+ # PEtab v2 -- no parameter scaling
455+ x_fixed_vals = self .petab_problem .x_nominal_fixed
456+ lb = self .petab_problem .lb
457+ ub = self .petab_problem .ub
458+ x_scales = [petab .LIN for x_id in x_ids ]
459+ prior = self ._create_prior_v2 ()
372460
373461 # Raise error if the correct calculator is not used.
374462 if self ._hierarchical :
@@ -388,19 +476,12 @@ def create_problem(
388476 map (x_ids .index , self .petab_problem .x_fixed_ids )
389477 )
390478
391- x_scales = [
392- self .petab_problem .parameter_df .loc [x_id , petab .PARAMETER_SCALE ]
393- for x_id in x_ids
394- ]
395-
396479 if problem_kwargs is None :
397480 problem_kwargs = {}
398481
399482 if startpoint_kwargs is None :
400483 startpoint_kwargs = {}
401484
402- prior = self .create_prior ()
403-
404485 if prior is not None :
405486 if self ._hierarchical :
406487 raise NotImplementedError (
0 commit comments