Does queueing a future method count as DML?

Using System.enqueueJob, Database.executeBatch, System.scheduleBatch, System.enqueueJob, and @future methods all modify the state of the database, so for purposes of callouts, count as a DML operation. This also means that Database.rollback can undo a scheduled job, batch job, queueable, or future method. Also note that any of those methods will prevent you from using PageReference.getContent, which counts as a callout, as well as web service methods from imported WSDL classes.


Example

public class q203304 {
    @future public static void x() {

    }
}

Execute Anonymous

q203304.x();
Blob c = new PageReference('https://www.google.com/').getContent();

Output:

Line: 2, Column: 1 System.CalloutException: You have uncommitted work pending. Please commit or rollback before calling out


It doesn't count as DML, however, queued asynchronous actions enter a queue to be executed after the present transaction. If the Apex transaction rolls back, so does the queue.

You could use try/catch to actually catch the callout exception and then do your DML afterwards to record what the outcome was.

If what you really want is to log something before or between callouts, that remains logged even if you reach an uncaught exception, look into Platform Events as a way to initiate this. Platform Events do NOT roll back, and you can hang triggers or Process Builders off of them to ensure some log is created.

See Andrew Fawcett's Dreamforce talk on this topic: https://www.youtube.com/watch?v=yYeurYnasVc