3
\$\begingroup\$

I am looking for some way to improve my code. It works but it doesn't look good and I am almost sure that lot of Best Practices rules are violated.

The save_session() function, creates dictionary with other dictionaries nested in. At the end the dictionary is dump to .json file.

I will appreciate any suggestions and advice for improvement of this code.

For better understanding the code of save_session():

workouts_instances is the list of current WorkoutPlan instances,

WorkoutPlan stores instances of Training and Exercise,

Training stores instances of Exercise,

class WorkoutPlan:
    def __init__(self, name, trainings=list(), exercises=list()):
        self.name = name
        self.trainings = trainings
        self.exercises = exercises
    ...

class Training:
    def __init__(self, name, exercises=list()):
        self.name = name
        self.exercises = exercises
    ...

class Exercise:
    def __init__(self, name, details=dict()):
        self.name = name
        self.details = details
    ...

Here is the code of save_session():

def save_session():
    """Exports current data to .json file."""
    data_to_save = {}

    # add workout plans
    for workout in workouts_instances:
        data_to_save[workout.name] = {}

        # add trainings
        if workout.trainings:
            data_to_save[workout.name]["trainings"] = {}

            for training in workout.trainings:
                data_to_save[workout.name]["trainings"][training.name] = {}

                # add training exercises
                if training.exercises:
                    data_to_save[workout.name]["trainings"][training.name]['exercises'] = {
                        exercise.name: {} for exercise in training.exercises
                    }

                    for exercise in training.exercises:

                        if exercise.details:
                            data_to_save[workout.name]["trainings"][training.name]['exercises'][exercise.name][
                                'details'] = {detail: value for detail, value in
                                              exercise.details.items()}

        # add exercises
        if workout.exercises:
            data_to_save[workout.name]["exercises"] = {}

            exercises_to_save = data_to_save[workout.name]["exercises"]

            for exercise in workout.exercises:
                exercises_to_save[exercise.name] = {}

                if exercise.details:
                    details = exercise.details
                    exercises_to_save[exercise.name]['details'] = {detail: value for detail, value in details.items()}

    with open(WORKOUTS_FILE, 'w') as json_file:
        json.dump(data_to_save, json_file, indent=4)

and here is the example of output, data stored in .json file:

{
    "FBV - Full Body Workout": {
        "trainings": {
            "Training A": {
                "exercises": {
                    "squats": {
                        "details": {
                            "description": "squats with barbell",
                            "series": 4,
                            "repeats": 4,
                            "load": 70
                        }
                    }
                }
            }
        },
        "exercises": {
            "some exercise name": {
                "details": {
                    "description": "some description",
                    "series": 5,
                    "repeats": 5,
                    "load": 60
                }
            },
            "bench press - wide": {
                "details": {
                    "description": "bench press with wide grip",
                    "series": 5,
                    "repeats": 5,
                    "load": 60
                }
            }
        }
    }
}
\$\endgroup\$
5
  • \$\begingroup\$ It would be better if you provide the code calling the function or example usage as well. \$\endgroup\$
    – pacmaninbw
    Commented Jun 8, 2019 at 13:29
  • \$\begingroup\$ @pacmaninbw: save_session() is one of the menu options in console app. All it has to do is to write data into dictionaries and dump it to .json later. All I want to know is how to build this dictionary of nested dictionaries in more proper way than it is right now. \$\endgroup\$
    – jbb
    Commented Jun 8, 2019 at 13:38
  • 1
    \$\begingroup\$ Right now the question is off-topic please see codereview.stackexchange.com/help/dont-ask and codereview.stackexchange.com/help/how-to-ask. By asking for examples of use I was trying to improve the question. \$\endgroup\$
    – pacmaninbw
    Commented Jun 8, 2019 at 13:43
  • 2
    \$\begingroup\$ Simply put, if you add example input and output it means it's easier for people to understand the transformation that is happening - help us, help you. \$\endgroup\$
    – Peilonrayz
    Commented Jun 8, 2019 at 13:51
  • \$\begingroup\$ I made some edits. Is it better now? \$\endgroup\$
    – jbb
    Commented Jun 8, 2019 at 14:40

1 Answer 1

1
\$\begingroup\$

Some suggestions:

  • Do not use mutable default arguments, they will mess with your subsequent calls. There are some very rare cases where mutable default arguments make sense, but this does not look like one of those.
  • Split generation of data from saving that data to a file. That way either method can be reused. If you also pull out the file handle to a main method you can dependency inject the file handle and test the whole functionality.
  • details have the same pattern everywhere, so they should also be a class or should be part of Exercise.
  • Like most Python code this could benefit from type annotations using MyPy.
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.