Melt butter in olive oil in a Dutch oven over medium-high heat. Add onions and celery and sauté for 5 minutes. Add garlic and red pepper flakes (if using) and sauté 30 seconds. Sprinkle in flour and cook, while stirring, an additional 2 minutes.: The pan will smell sweet and savory as the onion and celery soften, and you should hear a gentle sizzle that signals proper heat. The aroma of softened vegetables becomes mellow, and the brief goldening of the aromatics gives a toasty, warm scent that promises depth. When you add the minced garlic , a bright, nutty note will lift the pan fragrance for just a moment before you add the flour . Stirring the flour into the fat creates a paste that initially looks chalky, then becomes glossy and slightly nutty as you cook it for a couple of minutes, which removes any raw flour taste. If you skip this step or undercook the roux, the final soup can taste pasty or floury, so resist the urge to rush. Watch that the garlic does not brown, because burnt garlic yields bitterness that is hard to mask. Use a wooden spoon to scrape the bottom so nothing sticks, and if the pan seems too hot, lower the heat to keep the aromatics soft rather than browned.
Turn heat to low and stir in chicken broth. Whisk cornstarch with milk (you can whisk with as little as 1 cup milk, just enough so it dissolves) and add to pot. Add chicken, Dijon, bay leaves and all seasonings.: As the broth hits the roux, the mixture will seem thin at first, then slowly thicken as you integrate the milk and cornstarch slurry. You will notice steam rising and a gentle bubbling as the starch hydrates, giving the base a silkier body. The Dijon brings a faint piquancy that brightens the savory notes, and the bay leaf offers an understated herbal scent that mellows during simmering. When you nestle in the pieces of chicken , they should be submerged so they cook evenly, and you will see the broth shimmer as it warms. A common error here is adding undissolved cornstarch which can clump, so always whisk until perfectly smooth. Keep the heat low to avoid scorching the dairy components later in the process.
Increase heat to high, cover pot and bring to a boil. Reduce to a gentle simmer and keep covered. Simmer for 20 - 25 minutes, stirring occasionally and replacing lid, until chicken is tender enough to shred with a fork. Remove chicken to a cutting board and shred when cool enough to handle.: When you raise the heat, the pot will come to a brisk boil with lively bubbles, and you should then immediately lower to a gentle simmer where small, steady bubbles whisper rather than roar. That quieter bubble action gently breaks down connective tissues in the chicken , yielding tender, shreddable meat without drying it out. You may hear an occasional soft pop as the soup breathes through the lid. Resist lifting the lid too often, because steady heat helps cook evenly, but stirring occasionally prevents sticking around the edges. If the simmer is too aggressive the dairy can break or the liquid can reduce too much, concentrating salt and altering balance. Once the chicken shreds easily, the meat will appear moist and fibrous, indicating it is ready to be removed and shredded.
Meanwhile, add half and half to the soup and bring to a simmer. Stir in gnocchi and shredded carrots and simmer for 3 to 4 minutes or just until the gnocchi are cooked. Stir in spinach and shredded chicken and heat through, approximately 1 minute.: The moment you pour in the half and half , the soup gains a creamier sheen and the scent softens into a rich, dairy warmth. Adding the gnocchi introduces pillowy pieces that quickly swell and become tender, with a gentle plumpness you can see and feel when stirring. The matchstick carrots release a faint sweet aroma as they warm, balancing the savory base. Cooking gnocchi for just a few minutes is crucial, because overcooking causes them to disintegrate into the broth. When you fold in the chopped spinach , it will instantly wilt, adding a vivid green ribbon and fresh, vegetal notes that lighten the creaminess. Then add the shredded chicken to warm through, taking care not to simmer so long that the milk proteins separate. A frequent slip at this stage is letting the pot boil hard, which can break the dairy into an unpleasant texture.
Season with salt and pepper to taste (I like more salt) and add additional half and half or milk if desired for a less 'chunky' soup and warm through.: Tasting is everything here, because the ingredients you started with determine how much seasoning the final pot needs. Add salt in small increments, tasting between additions, and balance with cracked black pepper to lift flavors. If the soup feels too thick or has too many chunky pieces, a splash more half and half or milk will smooth it and bring it to your preferred consistency. The aroma will open up as you season, revealing subtler layers. Avoid over salting, which is hard to reverse, and be mindful that any added bouillon or packaged products may already contain salt.
Garnish individual servings with Parmesan and fresh parsley if desired.: A final garnish of grated Parmesan and a sprinkle of chopped parsley introduces an umami lift and a herbaceous brightness that rounds each bowl. The cheese will melt slightly into the warm surface, adding a nutty saltiness that ties the elements together, while parsley gives color contrast and a fresh finish. Add garnishes just before serving so they keep texture and appearance. A mistake here is adding the herb too early which causes it to lose vibrancy.