Unlike xeraa good answer, we run as much as possible from within AWS.
The real benefits we get from this are that it allows us to use the centralized Jenkins servers that run Ansible (and Terraform in our case to actually provide AWS with Ansible, which was only used to set up EC2 instances and run administrative books for administrative tasks).
We can then control access to these Jenkins servers through credentials and / or security groups / NACLs.
The implementation of this method means that we can control the number of people who have some credentials that will allow them to create everything that they like and / or destroy everything that they like.
Ideally, we only provide credentials to Jenkins servers through the IAM EC2 instance roles, but we are not quite there yet.
One of the real benefits of this is that our front / second line supports guys who use Windows, pretty much exclusively get access to a good web-based GUI to manage things in the middle of the night and run Jenkins jobs in which they specifically have access to which will perform operations such as restarting the server / service or even recovering part of the VPC.
We have a separate "dev" account with which developers have access to their own machines, and here we build things when we develop our Ansible database (and Terraform) before this code base is used in our test and production conditions.
source share