Model = data and business logic. ViewModel = prepares data for display. View = XAML UI that binds to the ViewModel. The ViewModel never references the View — communication is entirely through bindings.
public partial class WeatherViewModel : ObservableObject { private readonly IWeatherService _svc; [ObservableProperty] bool _isLoading; [ObservableProperty] string _errorMessage = ""; [ObservableProperty] ObservableCollection<Forecast> _forecasts = []; public WeatherViewModel(IWeatherService svc) => _svc = svc; [RelayCommand] async Task LoadAsync() { IsLoading = true; ErrorMessage = ""; try { var data = await _svc.GetForecastAsync(); Forecasts = new ObservableCollection<Forecast>(data); } catch (Exception ex) { ErrorMessage = ex.Message; } finally { IsLoading = false; } } }