dnspython's design was around "duck typing", so many things return generic types. You've got two basic options:
1) Tell mypy what the actual type is:
from dns.rdtypes.ANY.SOA import SOA
from typing import cast
for (name, ttl, rdata) in zone.iterate_rdatas("SOA"):
rdata = cast(SOA, rdata)
serial_nr = rdata.serial # ok
bogus = rdata.bogus # mypy rejects; also fails at runtime
2) Use an rdata variable of type Any, either implicitly from an Any-typed API or explicitly:
# implicit
for rdata in zone.find_rdataset("@", "SOA"):
serial_nr = rdata.serial # ok as the iterator's values are Any
bogus = rdata.bogus # mypy does not complain; fails at runtime
# explicit
rdata: Any
for (name, ttl, rdata) in zone.iterate_rdatas("SOA"):
serial_nr = rdata.serial # ok
bogus = rdata.bogus # mypy does not complain; fails at runtime