These environments must model the target systems, and they must be as close as is practical to those target systems. That doesn't mean you need to make exact copies of expensive production environments but you do need to create models of production environments that test most of the pieces your code will come in contact. Having models that mirror production systems means that when you move your code to production you'll introduce fewer changes with unintended consequences. Your changes will have already existed in a production-like environment. You can take comfort in knowing that the changes you enact in these models will be the same changes that will appear on the target system.
Ideally you'll need to have an environment like this on a machine that you control. This means that you're not competing with other programmers in your organization who are also being brave with their changes. But you'll also want to ensure that you keep your environment up-to-date with their changes (and any production changes) so your development model matches what's on the target system and what will be on the target system. A good model is one that is kept current with what it is modeling. It's the same as a map of a city: it's best when it matches the area its modeling and is kept current with changes that occur in that city. A good map of the city might tell you about the recent construction happening on your route. A useless map doesn't even show your route because it wasn't built when the map was created. If our model of production is constantly falling behind what's in production we will spend more time rectifying the changes that we're making with the changes between our model and production.
These environments must model the target systems, and they must be as close as is practical to those target systems. That doesn't mean you need to make exact copies of expensive production environments but you do need to create models of production environments that test most of the pieces your code will come in contact. Having models that mirror production systems means that when you move your code to production you'll introduce fewer changes with unintended consequences. Your changes will have already existed in a production-like environment. You can take comfort in knowing that the changes you enact in these models will be the same changes that will appear on the target system.
Ideally you'll need to have an environment like this on a machine that you control. This means that you're not competing with other programmers in your organization who are also being brave with their changes. But you'll also want to ensure that you keep your environment up-to-date with their changes (and any production changes) so your development model matches what's on the target system and what will be on the target system. A good model is one that is kept current with what it is modeling. It's the same as a map of a city: it's best when it matches the area its modeling and is kept current with changes that occur in that city. A good map of the city might tell you about the recent construction happening on your route. A useless map doesn't even show your route because it wasn't built when the map was created. If our model of production is constantly falling behind what's in production we will spend more time rectifying the changes that we're making with the changes between our model and production.