- Bruno Fernandes (2' Pen)
- Luke Shaw (50')
The result sees Ole Gunnar Solskjaer's side leapfrog Leicester into second place and go 11 points behind leaders City.
United have now gone 22 matches unbeaten away from home and it was also the first time they won a league game against the "Big Six" teams this season.
The only negative point for United was that Marcus Rashford came off with an injury in the second half.
"When you come away with a 2-0 win and another clean sheet and a performance like this then you are delighted," Solskjaer told Sky Sports.
"Every game is different. We went back to be a little bit what we wanted to be and that's being direct."
City went close to an equaliser right after the break but Rodri's strike clipped the top of the bar.
United grabbed a second goal moments later when Shaw started and finished a swift attack with a calm finish into the bottom corner.
The visitors almost scored a third after 68 minutes when Martial was through on goal but Ederson saved from close range.
City pressed but United held on to keep their slim hopes of winning the title alive.
"Congratulations Manchester United first of all," City boss Pep Guardiola told BBC postmatch. "Against West Ham we played much, much worse than today.
"Against West Ham we didn't deserve to win and maybe today we didn't deserve to lose. We were not good in front of goal, our strikers were not brilliant today but it happens."
|Brighton & Hove Albion||14||6||4||4||+4||22|
|West Ham United||14||6||3||5||0||21|