Actually Ive done this.
What I would say is that if you are planning to it your self it requires some amount of time and expertise if you really want to implement a custom solution that can integrate with your web platform. I did some research and in the end this is how I did it.
I use Bitcoind
It runs on a private server well away from the web server.
On the private server there are several encrypted wallets running on different ports under different user accounts each of them runs the RPC deamon that only responds to ssl from the local host.
Users have an account on on the web application, when they are created they are assigned to one of the private wallets and given an account in that wallet.
The web application sends an RPC request for getaddress using a message queue that a process on the private server listens to. This issues a new address for payment and puts it in the web applications database.
When we want to accept payment we display the new address to the user on the web page
On the private server a deamon runs every minute or so that calls getreceivedbyaddress -minconf with the addresses we have displayed to users to receive payment.
when it sees a new payment it updates the webservers database with the record of the payment.
To make it more complicated but secure the communication is also encrypted and the details of the transaction signed using a shared secret between the web server and the wallet daemon process. So for example the web application wont regard the payment as accepted until it sees a signed transaction in its database and the deamon wont put one there until it has seen the minimum number of transactions confirmations on the network.
It took me a couple of days to implement but I had quite a big head start.
The easiest way is to go with one of the payment vendors who have done the hard work for you unless you plan on becoming one of them.
There are several other gotyas you have to be aware of.. for example
Keeping a secure backup of the remote wallets
Keeping the address pool in the remote wallets primed and making sure you have backed up the wallet after priming it.
Storing the wallet pass-phrases so you don't lock your self out
having a way to change them..
What I do is have a multi signature approach where half the wallet phrase is sotred in the daemon binary so the developer could get hold of it.. The other half entered at run time by the support guy. Neither of them would have the full pass phrase so cant steel the wallet and run away with it easily.
Regarding the problem of creating too many addresses and not being able to remove them.
At them moment this is not a problem for us as our solution will scale as we get more users we can create more wallets.
As for cold storage I'm not completely convinced this offers us any more security than we have now with out giving us more problems associated with managing the cold part of the storage. At the moment its a numbers game. where by if we only have $5000 in a wallet its probably not worth it. If we have $3 million in a wallet then we would firstly be ecstatic our business was that successful, Then probably invest in a more secure private data center some brand new servers and some very clever security people