After exchanging the auth code for an access token, I AM able to access the Web API resources. Example: GET https://domain.api.crm.dynamics.com/api/data/v9.1/contacts. BUT, my permissions are only for user impersonation. So, my Oauth token request does not provide a refresh token, and the scope is limited to user_impersonation.
On the API Permissions screen, I can only add "Delegated permissions", and user_impersonation is the only option. I would have hoped to add "Application permissions". If that's not what I need, what am I missing? How do I get application-level permission to the Web API, with a refresh token?