In a medium bowl, combine ground beef, breadcrumbs, Parmesan, egg, minced garlic, Italian seasoning, salt, and pepper. Mix gently with your hands until just combined – overmixing can make the meatballs tough. For perfectly uniform meatballs, use a small cookie scoop (about 1 tablespoon size) to portion the mixture. Roll into approximately 20-24 small meatballs and set aside on a plate.
Heat 1 tablespoon of olive oil in a large Dutch oven or heavy-bottomed pot over medium-high heat. Working in batches if necessary, add the meatballs to the pot without overcrowding. Brown on all sides for about 2-3 minutes total – they don't need to be cooked through completely as they'll finish cooking in the soup. Transfer the browned meatballs to a clean plate and set aside.
In the same pot, add the remaining tablespoon of olive oil. Add onions, carrots, and celery, cooking for 4-5 minutes until vegetables begin to soften. Add the minced garlic and cook for another 30 seconds until fragrant. Stir in the tomato paste and cook for 1 minute, allowing it to slightly caramelize and coat the vegetables.
Add the diced tomatoes with their juice, chicken broth, dried basil, oregano, and red pepper flakes if using. Bring to a boil, then reduce to a simmer. Gently return the meatballs to the pot and cook for 10 minutes to allow flavors to meld and ensure the meatballs cook through.
Add the tortellini to the simmering soup and cook according to package directions, usually 7-8 minutes for fresh and 2-3 minutes longer for frozen. In the last 2 minutes of cooking, stir in the spinach and allow it to wilt. Taste and adjust seasoning with salt and pepper as needed.
Serve in deep bowls garnished with fresh basil or parsley and a sprinkle of grated Parmesan cheese.