diff --git a/.github/workflows/test-pytest.yaml b/.github/workflows/test-pytest.yaml index 68855c2..c73dd21 100644 --- a/.github/workflows/test-pytest.yaml +++ b/.github/workflows/test-pytest.yaml @@ -15,7 +15,7 @@ jobs: strategy: matrix: os: [ubuntu-latest, windows-latest] - python-version: [3.8, 3.12] + python-version: [3.9, 3.12] env: OS: ${{ matrix.os }} PYTHON: ${{ matrix.python-version }} diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..4a6e122 --- /dev/null +++ b/Makefile @@ -0,0 +1,20 @@ +lint: isort black + +isort: + isort . + +black: + black . + +pylint: + pylint rocketserializer/ --output="pylint_report.txt" + +tests: + pytest + +# tests-unit: + +# tests-acceptance: + +# tests-integration: + diff --git a/examples/EPFL--BellaLui--2020/parameters.json b/examples/EPFL--BellaLui--2020/parameters.json index 90f819a..581e7a9 100644 --- a/examples/EPFL--BellaLui--2020/parameters.json +++ b/examples/EPFL--BellaLui--2020/parameters.json @@ -42,7 +42,7 @@ "nozzle_radius": 0.02025, "position": 2.3379117844381234, "throat_radius": 0.0135, - "thrust_source": "examples/EPFL--BellaLui--2020/thrust_source.csv" + "thrust_source": "examples\\EPFL--BellaLui--2020\\thrust_source.csv" }, "nosecones": { "base_radius": 0.078, @@ -56,7 +56,7 @@ "rocket": { "center_of_mass_without_propellant": 1.559, "coordinate_system_orientation": "nose_to_tail", - "drag_curve": "examples/EPFL--BellaLui--2020/drag_curve.csv", + "drag_curve": "examples\\EPFL--BellaLui--2020\\drag_curve.csv", "inertia": [ 0.096246, 0.096246, @@ -66,13 +66,17 @@ "radius": 0.078 }, "stored_results": { + "burnout_stability_margin": 3.1703, "flight_time": 92.782, "ground_hit_velocity": 26.142, "launch_rod_velocity": 14.728, "max_acceleration": 122.07, "max_altitude": 1190.0, "max_mach": 0.5587, + "max_stability_margin": 4.8193, + "max_thrust": 1287.5, "max_velocity": 189.56, + "min_stability_margin": 0.85185, "time_to_apogee": 14.851 }, "tails": { diff --git a/examples/NDRT--Rocket--2020/parameters.json b/examples/NDRT--Rocket--2020/parameters.json index 2d34c2b..0a3e057 100644 --- a/examples/NDRT--Rocket--2020/parameters.json +++ b/examples/NDRT--Rocket--2020/parameters.json @@ -1,4 +1,5 @@ { + "elliptical_fins": {}, "environment": { "base_pressure": null, "base_temperature": null, @@ -84,13 +85,17 @@ "radius": 0.1016 }, "stored_results": { + "burnout_stability_margin": 3.7288, "flight_time": 86.725, "ground_hit_velocity": 4.7426, "launch_rod_velocity": 17.993, "max_acceleration": 67.386, "max_altitude": 1085.9, "max_mach": 0.42789, + "max_stability_margin": 3.7685, + "max_thrust": 1785.0, "max_velocity": 145.01, + "min_stability_margin": 1.2489, "time_to_apogee": 15.761 }, "tails": { diff --git a/examples/ProjetoJupiter--Valetudo--2019/parameters.json b/examples/ProjetoJupiter--Valetudo--2019/parameters.json index 84168b8..f57c4e6 100644 --- a/examples/ProjetoJupiter--Valetudo--2019/parameters.json +++ b/examples/ProjetoJupiter--Valetudo--2019/parameters.json @@ -1,4 +1,5 @@ { + "elliptical_fins": {}, "environment": { "base_pressure": 94311.0, "base_temperature": 300.76, @@ -81,13 +82,17 @@ "radius": 0.04045000000000001 }, "stored_results": { + "burnout_stability_margin": 2.4363, "flight_time": 64.161, "ground_hit_velocity": 18.146, "launch_rod_velocity": 26.397, "max_acceleration": 108.52, "max_altitude": 882.42, "max_mach": 0.36177, + "max_stability_margin": 3.2714, + "max_thrust": 1067.7, "max_velocity": 125.47, + "min_stability_margin": 0.0, "time_to_apogee": 14.65 }, "tails": {}, diff --git a/pyproject.toml b/pyproject.toml index 1525d05..4a777d8 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -76,4 +76,5 @@ disable = """ raise-missing-from, fixme, no-else-break, + no-else-return, """ diff --git a/rocketserializer/components/stored_results.py b/rocketserializer/components/stored_results.py index ab762a7..d4cd511 100644 --- a/rocketserializer/components/stored_results.py +++ b/rocketserializer/components/stored_results.py @@ -1,11 +1,13 @@ import logging +import numpy as np + from .._helpers import _dict_to_string logger = logging.getLogger(__name__) -def search_stored_results(bs): +def search_stored_results(bs, datapoints, data_labels, time_vector, burnout_position): """Search for the stored simulation results in the bs and return the settings as a dict. @@ -22,11 +24,9 @@ def search_stored_results(bs): "flighttime", "groundhitvelocity" and "launchrodvelocity". """ settings = {} - sim = bs.find("simulation") sim_data = sim.find("flightdata") logger.info("Found the 'flightdata' tag in the 'simulation' tag.") - name_map = { "max_altitude": "maxaltitude", "max_velocity": "maxvelocity", @@ -44,8 +44,84 @@ def search_stored_results(bs): "Retrieved the '%s' value from the .ork file: %s", key, settings[key] ) + settings["max_stability_margin"] = __get_parameter( + datapoints, + data_labels, + time_vector, + "Stability margin calibers", + position="max", + ) + settings["min_stability_margin"] = __get_parameter( + datapoints, + data_labels, + time_vector, + "Stability margin calibers", + position="min", + ) + settings["burnout_stability_margin"] = __get_parameter( + datapoints, + data_labels, + time_vector, + "Stability margin calibers", + position=burnout_position, + ) + settings["max_thrust"] = __get_parameter( + datapoints, data_labels, time_vector, "Thrust", position="max" + ) + logger.info( "The flight data was successfully retrieved:\n%s", _dict_to_string(settings, indent=23), ) return settings + + +def __get_parameter(datapoints, data_labels, time_vector, label, position): + """Get the latitude and longitude from the .ork file. + Parameters + ---------- + label : str + Latitude or longitude. + datapoints : list + List of datapoints from the .ork file. + data_labels : list + List of labels for the datapoints. + time_vector : list + The time vector of the simulation. + position : str or int + The position to get the value from. Can be "last", "first", "max", "min" + or an integer. + """ + + parameter = [ + float(datapoint.text.split(",")[data_labels.index(label)]) + for datapoint in datapoints + ] + # convert to numpy array + parameter = np.array([time_vector, parameter]).T + # sort by time + parameter = parameter[parameter[:, 0].argsort()] + # clip the curve to remove negative values + parameter[parameter[:, 1] < 0, 1] = 0 + # Assuming parameter is a NumPy array and 'NaN' values are represented as np.nan + # This will keep rows where the second column is not NaN + parameter = parameter[~np.isnan(parameter[:, 1])] + + if isinstance(position, str): + if position == "last": + # return the end point (final time, final value) + return parameter[-1, 1] + elif position == "first": + # return the first point (initial time, initial value) + return parameter[0, 1] + elif position == "max": + return np.max(parameter[:, 1]) # return the maximum value + elif position == "min": + return np.min(parameter[:, 1]) # return the minimum value + else: + pass + if isinstance(position, np.int64): + return parameter[position, 1] # return the value at the specified position + else: + logger.error("Invalid position parameter") + raise ValueError("Error in position parameter") diff --git a/rocketserializer/ork_extractor.py b/rocketserializer/ork_extractor.py index 8abd39a..fc5280c 100644 --- a/rocketserializer/ork_extractor.py +++ b/rocketserializer/ork_extractor.py @@ -88,7 +88,9 @@ def ork_extractor(bs, filepath, output_folder, ork, eng): transitions = search_transitions(bs, elements, ork) rail_buttons = search_rail_buttons(bs, elements) parachutes = search_parachutes(bs) - stored_results = search_stored_results(bs) + stored_results = search_stored_results( + bs, datapoints, data_labels, time_vector, burnout_position + ) # save everything to a dictionary settings["id"] = id_info diff --git a/run-tests.ps1 b/run-tests.ps1 index cf2bc43..416eb7c 100644 --- a/run-tests.ps1 +++ b/run-tests.ps1 @@ -1,3 +1,9 @@ ork2json --filepath="examples\EPFL--BellaLui--2020\rocket.ork" ork2json --filepath="examples\NDRT--Rocket--2020\rocket.ork" ork2json --filepath="examples\ProjetoJupiter--Valetudo--2019\rocket.ork" +ork2json --filepath="examples\WERT--Prometheus--2022\rocket.ork" + +ork2ipynb --filepath="examples\EPFL--BellaLui--2020\rocket.ork" +ork2ipynb --filepath="examples\NDRT--Rocket--2020\rocket.ork" +ork2ipynb --filepath="examples\ProjetoJupiter--Valetudo--2019\rocket.ork" +ork2ipynb --filepath="examples\WERT--Prometheus--2022\rocket.ork" diff --git a/tests/acceptance/EPFL--BellaLui--2020/parameters.json b/tests/acceptance/EPFL--BellaLui--2020/parameters.json index fc7f04e..4c1151e 100644 --- a/tests/acceptance/EPFL--BellaLui--2020/parameters.json +++ b/tests/acceptance/EPFL--BellaLui--2020/parameters.json @@ -96,6 +96,10 @@ "time_to_apogee": 14.851, "flight_time": 92.782, "ground_hit_velocity": 26.142, - "launch_rod_velocity": 14.728 + "launch_rod_velocity": 14.728, + "max_stability_margin": 4.8193, + "min_stability_margin": 0.85185, + "burnout_stability_margin": 3.1703, + "max_thrust": 1287.5 } } \ No newline at end of file diff --git a/tests/acceptance/NDRT--Rocket--2020/parameters.json b/tests/acceptance/NDRT--Rocket--2020/parameters.json index 23616b8..5105b69 100644 --- a/tests/acceptance/NDRT--Rocket--2020/parameters.json +++ b/tests/acceptance/NDRT--Rocket--2020/parameters.json @@ -115,6 +115,10 @@ "time_to_apogee": 15.761, "flight_time": 86.725, "ground_hit_velocity": 4.7426, - "launch_rod_velocity": 17.993 + "launch_rod_velocity": 17.993, + "max_stability_margin": 3.7685, + "min_stability_margin": 1.2489, + "burnout_stability_margin": 3.7288, + "max_thrust": 1785.0 } } \ No newline at end of file diff --git a/tests/acceptance/ProjetoJupiter--Valetudo--2019/parameters.json b/tests/acceptance/ProjetoJupiter--Valetudo--2019/parameters.json index e410b2b..a282666 100644 --- a/tests/acceptance/ProjetoJupiter--Valetudo--2019/parameters.json +++ b/tests/acceptance/ProjetoJupiter--Valetudo--2019/parameters.json @@ -104,6 +104,10 @@ "time_to_apogee": 14.65, "flight_time": 64.161, "ground_hit_velocity": 18.146, - "launch_rod_velocity": 26.397 + "launch_rod_velocity": 26.397, + "max_stability_margin": 3.2714, + "min_stability_margin": 0.0, + "burnout_stability_margin": 2.4363, + "max_thrust": 1067.7 } } \ No newline at end of file