Repository: qiboteam/qibocal
Issue: Issues found while calibrating with QM

Here is a list of issues I had during the second round of calibrations using QM and the qmsweepers branch (PR #195 - synced with latest main):

* The `update_platform_runcard` method of `ActionBuilder` fails in some indexing
```py
params = data_fit.df.to_dict("index")[qubit if qubit == 0 else qubit - 1]
```
when using more than one qubits with qubit 0 included. In fact this indexing does not look right to me.
* Rabi-amplitude MSR plot fails with `KeyError: 0` in line `data_fit.df["popt0"][0]`. This is fixed by using `float(data_fit.df["popt0"])`.
* Ramsey plot fails with the same error and the same fix also works.

I do not have time to test if these issues appear on main, but since they are related to plotting/fitting and not the data acquisition, I would expect that they will appear on main if a multiqubit platform is used. An easy way to check would be to use the `DummyPlatform` with one or more qubits. Also, I have not tested all routines yet so there may be other issues not reported.

It seems to me that most of these issues are related to wrong indexing of pandas DataFrame: particularly the fact that DataFrame indeces are not affected when slicing the DataFrame with conditions. I believe that moving to numpy dtypes would simplify this a lot.

Changed files:
src/qibocal/calibrations/characterization/ramsey.py, src/qibocal/fitting/methods.py, src/qibocal/plots/rabi.py, src/qibocal/plots/t1.py, src/qibocal/calibrations/characterization/t1.py, src/qibocal/plots/ramsey.py, src/qibocal/plots/spectroscopies.py, src/qibocal/plots/spin_echo.py, src/qibocal/plots/flipping.py, src/qibocal/cli/builders.py, src/qibocal/plots/allXY.py

diff --git a/src/qibocal/calibrations/characterization/ramsey.py b/src/qibocal/calibrations/characterization/ramsey.py
index 35d2643b..6fbc416e 100644
--- a/src/qibocal/calibrations/characterization/ramsey.py
+++ b/src/qibocal/calibrations/characterization/ramsey.py
@@ -92,7 +92,7 @@ def ramsey_frequency_detuned(
     # DataUnits stores by default MSR, phase, i, q
     # additionally include wait time and t_max
     data = DataUnits(
-        name=f"data",
+        name="data",
         quantities={"wait": "ns", "t_max": "ns"},
         options=["qubit", "iteration"],
     )
@@ -178,12 +178,11 @@ def ramsey_frequency_detuned(
                     "T2",
                 ],
             )
-
         stop = False
         for qubit in qubits:
-            new_t2 = float(data_fit.df[data_fit.df["qubit"] == qubit]["T2"][0])
+            new_t2 = float(data_fit.df[data_fit.df["qubit"] == qubit]["T2"])
             corrected_qubit_freq = int(
-                data_fit.df[data_fit.df["qubit"] == qubit]["drive_frequency"][0]
+                data_fit.df[data_fit.df["qubit"] == qubit]["drive_frequency"]
             )
 
             if new_t2 > qubits[qubit].T2 and len(delay_between_pulses_end) > 1:
diff --git a/src/qibocal/calibrations/characterization/t1.py b/src/qibocal/calibrations/characterization/t1.py
index 4d0038ca..0acfae43 100644
--- a/src/qibocal/calibrations/characterization/t1.py
+++ b/src/qibocal/calibrations/characterization/t1.py
@@ -112,7 +112,7 @@ def t1(
                 r.update(
                     {
                         "wait[ns]": wait,
-                        "qubit": qubit,
+                        "qubit": ro_pulse.qubit,
                         "iteration": iteration,
                     }
                 )
diff --git a/src/qibocal/cli/builders.py b/src/qibocal/cli/builders.py
index 6cd37188..c1c297af 100644
--- a/src/qibocal/cli/builders.py
+++ b/src/qibocal/cli/builders.py
@@ -274,7 +274,7 @@ class ActionBuilder:
         except FileNotFoundError:
             return None
 
-        params = data_fit.df.to_dict("index")[qubit if qubit == 0 else qubit - 1]
+        params = data_fit.df[data_fit.df["qubit"] == qubit]
         settings = load_yaml(f"{self.folder}/new_platform.yml")
         for param in params:
             if param in list(self.qubits[qubit].__annotations__.keys()):
diff --git a/src/qibocal/fitting/methods.py b/src/qibocal/fitting/methods.py
index e14fc1af..9461f635 100644
--- a/src/qibocal/fitting/methods.py
+++ b/src/qibocal/fitting/methods.py
@@ -204,33 +204,35 @@ def lorentzian_fit(data, x, y, qubits, resonator_type, labels, fit_file_name=Non
             fit_res = model_Q.fit(
                 data=voltages, frequency=frequencies, params=guess_parameters
             )
+            # get the values for postprocessing and for legend.
+            f0 = fit_res.best_values["center"]
+            BW = fit_res.best_values["sigma"] * 2
+            Q = abs(f0 / BW)
+            peak_voltage = (
+                fit_res.best_values["amplitude"]
+                / (fit_res.best_values["sigma"] * np.pi)
+                + fit_res.best_values["offset"]
+            )
+
+            freq = f0
+
+            data_fit.add(
+                {
+                    labels[0]: freq,
+                    labels[1]: peak_voltage,
+                    "popt0": fit_res.best_values["amplitude"],
+                    "popt1": fit_res.best_values["center"],
+                    "popt2": fit_res.best_values["sigma"],
+                    "popt3": fit_res.best_values["offset"],
+                    "qubit": qubit,
+                }
+            )
         except:
             log.warning("lorentzian_fit: the fitting was not successful")
-            data_fit.add({key: 0 for key in data_fit.df.columns})
-            return data_fit
-
-        # get the values for postprocessing and for legend.
-        f0 = fit_res.best_values["center"]
-        BW = fit_res.best_values["sigma"] * 2
-        Q = abs(f0 / BW)
-        peak_voltage = (
-            fit_res.best_values["amplitude"] / (fit_res.best_values["sigma"] * np.pi)
-            + fit_res.best_values["offset"]
-        )
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
 
-        freq = f0
-
-        data_fit.add(
-            {
-                labels[0]: freq,
-                labels[1]: peak_voltage,
-                "popt0": fit_res.best_values["amplitude"],
-                "popt1": fit_res.best_values["center"],
-                "popt2": fit_res.best_values["sigma"],
-                "popt3": fit_res.best_values["offset"],
-                "qubit": qubit,
-            }
-        )
     return data_fit
 
 
@@ -266,7 +268,7 @@ def rabi_fit(data, x, y, qubits, resonator_type, labels):
     """
 
     data_fit = Data(
-        name=f"fits",
+        name="fits",
         quantities=[
             "popt0",
             "popt1",
@@ -317,23 +319,24 @@ def rabi_fit(data, x, y, qubits, resonator_type, labels):
             pi_pulse_parameter = np.abs((1.0 / popt[2]) / 2)
             pi_pulse_peak_voltage = smooth_dataset.max()
             t2 = 1.0 / popt[4]  # double check T1
+            data_fit.add(
+                {
+                    "popt0": popt[0],
+                    "popt1": popt[1],
+                    "popt2": popt[2],
+                    "popt3": popt[3],
+                    "popt4": popt[4],
+                    labels[0]: pi_pulse_parameter,
+                    labels[1]: pi_pulse_peak_voltage,
+                    "qubit": qubit,
+                }
+            )
         except:
             log.warning("rabi_fit: the fitting was not succesful")
-            data_fit.add({key: 0 for key in data_fit.df.columns})
-            return data_fit
-
-        data_fit.add(
-            {
-                "popt0": popt[0],
-                "popt1": popt[1],
-                "popt2": popt[2],
-                "popt3": popt[3],
-                "popt4": popt[4],
-                labels[0]: pi_pulse_parameter,
-                labels[1]: pi_pulse_peak_voltage,
-                "qubit": qubit,
-            }
-        )
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
+
     return data_fit
 
 
@@ -374,7 +377,7 @@ def ramsey_fit(
             - **qubit**: The qubit being tested
     """
     data_fit = Data(
-        name=f"fits",
+        name="fits",
         quantities=[
             "popt0",
             "popt1",
@@ -431,24 +434,26 @@ def ramsey_fit(
             delta_phys = int((delta_fitting * sampling_rate) - offset_freq)
             corrected_qubit_frequency = int(qubit_freqs[qubit] + delta_phys)
             t2 = 1.0 / popt[4]
+
+            data_fit.add(
+                {
+                    "popt0": popt[0],
+                    "popt1": popt[1],
+                    "popt2": popt[2],
+                    "popt3": popt[3],
+                    "popt4": popt[4],
+                    labels[0]: delta_phys,
+                    labels[1]: corrected_qubit_frequency,
+                    labels[2]: t2,
+                    "qubit": qubit,
+                }
+            )
         except:
             log.warning("ramsey_fit: the fitting was not succesful")
-            data_fit.add({key: 0 for key in data_fit.df.columns})
-            return data_fit
-
-        data_fit.add(
-            {
-                "popt0": popt[0],
-                "popt1": popt[1],
-                "popt2": popt[2],
-                "popt3": popt[3],
-                "popt4": popt[4],
-                labels[0]: delta_phys,
-                labels[1]: corrected_qubit_frequency,
-                labels[2]: t2,
-                "qubit": qubit,
-            }
-        )
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
+
     return data_fit
 
 
@@ -520,21 +525,22 @@ def t1_fit(data, x, y, qubits, resonator_type, labels):
                 exp, times.values, voltages.values, p0=pguess, maxfev=2000000
             )
             t1 = abs(1 / popt[2])
+            data_fit.add(
+                {
+                    "popt0": popt[0],
+                    "popt1": popt[1],
+                    "popt2": popt[2],
+                    labels[0]: t1,
+                    "qubit": qubit,
+                }
+            )
 
         except:
             log.warning("t1_fit: the fitting was not succesful")
-            data_fit.add({key: 0 for key in data_fit.df.columns})
-            return data_fit
-
-    data_fit.add(
-        {
-            "popt0": popt[0],
-            "popt1": popt[1],
-            "popt2": popt[2],
-            labels[0]: t1,
-            "qubit": qubit,
-        }
-    )
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
+
     return data_fit
 
 
@@ -607,24 +613,22 @@ def flipping_fit(data, x, y, qubits, resonator_type, pi_pulse_amplitudes, labels
             corrected_amplitude = (
                 amplitude_correction_factor * pi_pulse_amplitudes[qubit]
             )
-            # angle = (niter * 2 * np.pi / popt[2] + popt[3]) / (1 + 4 * niter)
-            # amplitude_delta = angle * 2 / np.pi * pi_pulse_amplitude
+            data_fit.add(
+                {
+                    "popt0": popt[0],
+                    "popt1": popt[1],
+                    "popt2": popt[2],
+                    "popt3": popt[3],
+                    labels[0]: amplitude_correction_factor,
+                    labels[1]: corrected_amplitude,
+                    "qubit": qubit,
+                }
+            )
         except:
             log.warning("flipping_fit: the fitting was not succesful")
-            data_fit.add({key: 0 for key in data_fit.df.columns})
-            return data_fit
-
-        data_fit.add(
-            {
-                "popt0": popt[0],
-                "popt1": popt[1],
-                "popt2": popt[2],
-                "popt3": popt[3],
-                labels[0]: amplitude_correction_factor,
-                labels[1]: corrected_amplitude,
-                "qubit": qubit,
-            }
-        )
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
 
     return data_fit
 
@@ -696,22 +700,22 @@ def drag_tuning_fit(data: Data, x, y, qubits, labels):
             popt, pcov = curve_fit(cos, beta_params.values, voltages.values)
             smooth_dataset = cos(beta_params.values, popt[0], popt[1], popt[2], popt[3])
             beta_optimal = beta_params.values[np.argmin(smooth_dataset)]
-
+            data_fit.add(
+                {
+                    "popt0": popt[0],
+                    "popt1": popt[1],
+                    "popt2": popt[2],
+                    "popt3": popt[3],
+                    labels[0]: beta_optimal,
+                    "qubit": qubit,
+                }
+            )
         except:
             log.warning("drag_tuning_fit: the fitting was not succesful")
-            data_fit.add({key: 0 for key in data_fit.df.columns})
-            return data_fit
-
-        data_fit.add(
-            {
-                "popt0": popt[0],
-                "popt1": popt[1],
-                "popt2": popt[2],
-                "popt3": popt[3],
-                labels[0]: beta_optimal,
-                "qubit": qubit,
-            }
-        )
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
+
     return data_fit
 
 
@@ -833,7 +837,10 @@ def res_spectroscopy_flux_fit(data, x, y, qubit, fluxline, params_fit):
                 )
         except:
             log.warning("The fitting was not successful")
-            return data_fit
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
+
     else:
         data_fit = Data(
             name=f"fit1_q{qubit}_f{fluxline}",
@@ -849,16 +856,18 @@ def res_spectroscopy_flux_fit(data, x, y, qubit, fluxline, params_fit):
             popt = curve_fit(line, curr, freq_norm)[0]
             popt[0] = popt[0] * (freq_max - freq_min)
             popt[1] = popt[1] * (freq_max - freq_min) + freq_min
+            data_fit.add(
+                {
+                    "popt0": popt[0],  # C_ij
+                    "popt1": popt[1],
+                }
+            )
         except:
             log.warning("The fitting was not successful")
-            return data_fit
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
 
-        data_fit.add(
-            {
-                "popt0": popt[0],  # C_ij
-                "popt1": popt[1],
-            }
-        )
     return data_fit
 
 
@@ -954,19 +963,21 @@ def spin_echo_fit(data, x, y, qubits, resonator_type, labels):
             )
             t2 = abs(1 / popt[2])
 
+            data_fit.add(
+                {
+                    "popt0": popt[0],
+                    "popt1": popt[1],
+                    "popt2": popt[2],
+                    labels[0]: t2,
+                    "qubit": qubit,
+                }
+            )
         except:
             log.warning("spin_echo_fit: the fitting was not succesful")
-            return data_fit
-
-    data_fit.add(
-        {
-            "popt0": popt[0],
-            "popt1": popt[1],
-            "popt2": popt[2],
-            labels[0]: t2,
-            "qubit": qubit,
-        }
-    )
+            data_fit.add(
+                {key: 0 if key != "qubit" else qubit for key in data_fit.df.columns}
+            )
+
     return data_fit
 
 
diff --git a/src/qibocal/plots/allXY.py b/src/qibocal/plots/allXY.py
index a404c193..c94ee63f 100644
--- a/src/qibocal/plots/allXY.py
+++ b/src/qibocal/plots/allXY.py
@@ -313,10 +313,10 @@ def drag_pulse_tuning(folder, routine, qubit, format):
                     x=beta_range,
                     y=cos(
                         beta_range,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
-                        data_fit.df["popt3"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
+                        float(data_fit.df["popt3"]),
                     ),
                     name=f"q{qubit}/r{report_n}: Fit",
                     line=go.scatter.Line(dash="dot"),
diff --git a/src/qibocal/plots/flipping.py b/src/qibocal/plots/flipping.py
index ced54ea6..be5caf65 100644
--- a/src/qibocal/plots/flipping.py
+++ b/src/qibocal/plots/flipping.py
@@ -103,10 +103,10 @@ def flips_msr(folder, routine, qubit, format):
                     x=flips_range,
                     y=flipping(
                         flips_range,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
-                        data_fit.df["popt3"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
+                        float(data_fit.df["popt3"]),
                     ),
                     name=f"q{qubit}/r{report_n}: Fit MSR",
                     line=go.scatter.Line(dash="dot"),
diff --git a/src/qibocal/plots/rabi.py b/src/qibocal/plots/rabi.py
index 492b7663..e8f177ff 100644
--- a/src/qibocal/plots/rabi.py
+++ b/src/qibocal/plots/rabi.py
@@ -128,11 +128,11 @@ def time_msr_phase(folder, routine, qubit, format):
                     x=timerange,
                     y=rabi(
                         timerange,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
-                        data_fit.df["popt3"][0],
-                        data_fit.df["popt4"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
+                        float(data_fit.df["popt3"]),
+                        float(data_fit.df["popt4"]),
                     ),
                     name=f"q{qubit}/r{report_n} Fit",
                     line=go.scatter.Line(dash="dot"),
@@ -293,11 +293,11 @@ def gain_msr_phase(folder, routine, qubit, format):
                     x=gainrange,
                     y=rabi(
                         gainrange,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
-                        data_fit.df["popt3"][0],
-                        data_fit.df["popt4"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
+                        float(data_fit.df["popt3"]),
+                        float(data_fit.df["popt4"]),
                     ),
                     name=f"q{qubit}/r{report_n} Fit",
                     line=go.scatter.Line(dash="dot"),
@@ -461,11 +461,11 @@ def amplitude_msr_phase(folder, routine, qubit, format):
                     x=amplituderange,
                     y=rabi(
                         amplituderange,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
-                        data_fit.df["popt3"][0],
-                        data_fit.df["popt4"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
+                        float(data_fit.df["popt3"]),
+                        float(data_fit.df["popt4"]),
                     ),
                     name=f"q{qubit}/r{report_n} Fit",
                     line=go.scatter.Line(dash="dot"),
diff --git a/src/qibocal/plots/ramsey.py b/src/qibocal/plots/ramsey.py
index 3703d549..b77d9657 100644
--- a/src/qibocal/plots/ramsey.py
+++ b/src/qibocal/plots/ramsey.py
@@ -108,11 +108,11 @@ def time_msr(folder, routine, qubit, format):
                     x=waitrange,
                     y=ramsey(
                         waitrange,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
-                        data_fit.df["popt3"][0],
-                        data_fit.df["popt4"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
+                        float(data_fit.df["popt3"]),
+                        float(data_fit.df["popt4"]),
                     ),
                     name=f"q{qubit}/r{report_n} Fit",
                     line=go.scatter.Line(dash="dot"),
diff --git a/src/qibocal/plots/spectroscopies.py b/src/qibocal/plots/spectroscopies.py
index cf8dfb27..2175c98e 100644
--- a/src/qibocal/plots/spectroscopies.py
+++ b/src/qibocal/plots/spectroscopies.py
@@ -142,10 +142,10 @@ def frequency_msr_phase(folder, routine, qubit, format):
                     x=freqrange,
                     y=lorenzian(
                         freqrange,
-                        data_fit.df.iloc[0]["popt0"],
-                        data_fit.df.iloc[0]["popt1"],
-                        data_fit.df.iloc[0]["popt2"],  # pylint: disable=E1101
-                        data_fit.df.iloc[0]["popt3"],  # pylint: disable=E1101
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
+                        float(data_fit.df["popt3"]),
                     ),
                     name=f"q{qubit}/r{report_n} Fit",
                     line=go.scatter.Line(dash="dot"),
@@ -557,6 +557,7 @@ def dispersive_frequency_msr_phase(folder, routine, qubit, format):
 
         try:
             fit_data_0 = load_data(folder, subfolder, routine, format, "fit_data_0")
+            fit_data_0.df = fit_data_0.df[fit_data_0.df["qubit"] == qubit]
         except:
             fit_data_0 = Data(
                 quantities=[
@@ -572,6 +573,7 @@ def dispersive_frequency_msr_phase(folder, routine, qubit, format):
 
         try:
             fit_data_1 = load_data(folder, subfolder, routine, format, "fit_data_1")
+            fit_data_1.df = fit_data_1.df[fit_data_1.df["qubit"] == qubit]
         except:
             fit_data_1 = Data(
                 quantities=[
@@ -669,10 +671,10 @@ def dispersive_frequency_msr_phase(folder, routine, qubit, format):
                         x=freqrange,
                         y=lorenzian(
                             freqrange,
-                            data_fit.df.iloc[0]["popt0"],
-                            data_fit.df.iloc[0]["popt1"],
-                            data_fit.df.iloc[0]["popt2"],
-                            data_fit.df.iloc[0]["popt3"],
+                            float(data_fit.df["popt0"]),
+                            float(data_fit.df["popt1"]),
+                            float(data_fit.df["popt2"]),
+                            float(data_fit.df["popt3"]),
                         ),
                         name=f"q{qubit}/r{report_n}: {label} Fit",
                         line=go.scatter.Line(dash="dot"),
@@ -769,9 +771,9 @@ def frequency_attenuation(folder, routine, qubit, format):
         col=1,
     )
     if len(data1) > 0:
-        opt_f = data1.get_values("frequency", "GHz")[0]
-        opt_att = data1.get_values("attenuation", "dB")[0]
-        opt_snr = data1.get_values("snr", "dimensionless")[0]
+        opt_f = float(data1.get_values("frequency", "GHz"))
+        opt_att = float(data1.get_values("attenuation", "dB"))
+        opt_snr = float(data1.get_values("snr", "dimensionless"))
         fig.add_annotation(
             dict(
                 font=dict(color="black", size=12),
@@ -866,18 +868,18 @@ def frequency_bias_flux(folder, routine, qubit, format):
                     100,
                 )
                 if int(j) == int(qubit):
-                    f_qs = data_fit.get_values("f_qs")[0]
-                    f_rs = data_fit.get_values("f_rs")[0]
-                    curr_qs = data_fit.get_values("curr_sp")[0]
-                    g = data_fit.get_values("g")[0]
-                    d = data_fit.get_values("d")[0]
-                    xi = data_fit.get_values("xi")[0]
-                    C_ii = data_fit.get_values("C_ii")[0]
-                    f_offset = data_fit.get_values("f_offset")[0]
+                    f_qs = float(data_fit.get_values("f_qs"))
+                    f_rs = float(data_fit.get_values("f_rs"))
+                    curr_qs = float(data_fit.get_values("curr_sp"))
+                    g = float(data_fit.get_values("g"))
+                    d = float(data_fit.get_values("d"))
+                    xi = float(data_fit.get_values("xi"))
+                    C_ii = float(data_fit.get_values("C_ii"))
+                    f_offset = float(data_fit.get_values("f_offset"))
                     text_data = f"Fluxline: {j} <br> freq_r{qubit}_sp = {f_rs :.4e} Hz <br> freq_q{qubit}_sp = {f_qs :.4e} Hz <br> curr_{qubit}_sp = {curr_qs :.2e} A <br> g = {g :.2e} Hz <br> d = {d :.2e} <br> xi = {xi :.2e} 1/A <br> C_{qubit}{j} = {C_ii :.4e} Hz/A <br> f_offset_q{qubit} = {f_offset :.4e} Hz"
                     if len(data_fit.df.keys()) != 10:
-                        Ec = data_fit.get_values("Ec")[0]
-                        Ej = data_fit.get_values("Ej")[0]
+                        Ec = float(data_fit.get_values("Ec"))
+                        Ej = float(data_fit.get_values("Ej"))
                         text_data += f" <br> Ec = {Ec :.3e} Hz <br> Ej = {Ej :.3e} Hz"
                         freq_r_fit = freq_r_mathieu
                         params = [
@@ -940,7 +942,7 @@ def frequency_bias_flux(folder, routine, qubit, format):
                         row=1,
                         col=k + 1,
                     )
-                    C_ij = data_fit.get_values("popt0")[0]
+                    C_ij = float(data_fit.get_values("popt0"))
                     fig.add_annotation(
                         dict(
                             font=dict(color="black", size=12),
diff --git a/src/qibocal/plots/spin_echo.py b/src/qibocal/plots/spin_echo.py
index 13169a45..915f98bd 100644
--- a/src/qibocal/plots/spin_echo.py
+++ b/src/qibocal/plots/spin_echo.py
@@ -112,9 +112,9 @@ def spin_echo_time_msr(folder, routine, qubit, format):
                     x=waitrange,
                     y=exp(
                         waitrange,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
                     ),
                     name=f"q{qubit}/r{report_n} Fit",
                     line=go.scatter.Line(dash="dot"),
diff --git a/src/qibocal/plots/t1.py b/src/qibocal/plots/t1.py
index 9b92b21b..1979ed7f 100644
--- a/src/qibocal/plots/t1.py
+++ b/src/qibocal/plots/t1.py
@@ -105,9 +105,9 @@ def t1_time_msr(folder, routine, qubit, format):
                     x=waitrange,
                     y=exp(
                         waitrange,
-                        data_fit.df["popt0"][0],
-                        data_fit.df["popt1"][0],
-                        data_fit.df["popt2"][0],
+                        float(data_fit.df["popt0"]),
+                        float(data_fit.df["popt1"]),
+                        float(data_fit.df["popt2"]),
                     ),
                     name=f"q{qubit}/r{report_n} Fit",
                     line=go.scatter.Line(dash="dot"),