A differentiable programming framework for spin models