|
1 | 1 | import traceback |
2 | | -import warnings |
3 | 2 | from pathlib import Path |
4 | 3 | from typing import List, Optional, Union |
5 | 4 |
|
@@ -79,3 +78,58 @@ def test_resource( |
79 | 78 | # todo: add tests for non-model resources |
80 | 79 |
|
81 | 80 | return {"error": error, "traceback": tb} |
| 81 | + |
| 82 | + |
| 83 | +def debug_model( |
| 84 | + model_rdf: Union[RawResourceDescription, ResourceDescription, URI, Path, str], |
| 85 | + *, |
| 86 | + weight_format: Optional[WeightsFormat] = None, |
| 87 | + devices: Optional[List[str]] = None, |
| 88 | +): |
| 89 | + """Run the model test and return dict with inputs, results, expected results and intermediates. |
| 90 | +
|
| 91 | + Returns dict with tensors "inputs", "inputs_processed", "outputs_raw", "outputs", "expected" and "diff". |
| 92 | + """ |
| 93 | + inputs: Optional = None |
| 94 | + inputs_processed: Optional = None |
| 95 | + outputs_raw: Optional = None |
| 96 | + outputs: Optional = None |
| 97 | + expected: Optional = None |
| 98 | + diff: Optional = None |
| 99 | + |
| 100 | + model = load_resource_description(model_rdf) |
| 101 | + if not isinstance(model, Model): |
| 102 | + raise ValueError(f"Not a bioimageio.model: {model_rdf}") |
| 103 | + |
| 104 | + prediction_pipeline = create_prediction_pipeline( |
| 105 | + bioimageio_model=model, devices=devices, weight_format=weight_format |
| 106 | + ) |
| 107 | + inputs = [xr.DataArray(np.load(str(in_path)), dims=input_spec.axes) |
| 108 | + for in_path, input_spec in zip(model.test_inputs, model.inputs)] |
| 109 | + |
| 110 | + inputs_processed, stats = prediction_pipeline.preprocess(*inputs) |
| 111 | + outputs_raw = prediction_pipeline.predict(*inputs_processed) |
| 112 | + outputs, _ = prediction_pipeline.postprocess(*outputs_raw, input_sample_statistics=stats) |
| 113 | + if isinstance(outputs, (np.ndarray, xr.DataArray)): |
| 114 | + outputs = [outputs] |
| 115 | + |
| 116 | + expected = [xr.DataArray(np.load(str(out_path)), dims=output_spec.axes) |
| 117 | + for out_path, output_spec in zip(model.test_outputs, model.outputs)] |
| 118 | + if len(outputs) != len(expected): |
| 119 | + error = ( |
| 120 | + f"Number of outputs and number of expected outputs disagree: {len(outputs)} != {len(expected)}" |
| 121 | + ) |
| 122 | + print(error) |
| 123 | + else: |
| 124 | + diff = [] |
| 125 | + for res, exp in zip(outputs, expected): |
| 126 | + diff.append(res - exp) |
| 127 | + |
| 128 | + return { |
| 129 | + "inputs": inputs, |
| 130 | + "inputs_processed": inputs_processed, |
| 131 | + "outputs_raw": outputs_raw, |
| 132 | + "outputs": outputs, |
| 133 | + "expected": expected, |
| 134 | + "diff": diff |
| 135 | + } |
0 commit comments