解决了语音上传到问题,接下来要解决下载播放问题

This commit is contained in:
joywayer
2025-06-15 12:36:47 +08:00
parent bba3ed1cb4
commit c11fc62bf1
513 changed files with 31197 additions and 2969 deletions

View File

@@ -0,0 +1,36 @@
//
// QNDnsError.h
// Doh
//
// Created by yangsen on 2021/7/20.
//
#import <Foundation/Foundation.h>
NS_ASSUME_NONNULL_BEGIN
extern const int kQNDomainHijackingCode;
extern const int kQNDomainNotOwnCode;
extern const int kQNDomainSeverError;
extern const int kQNDnsMethodErrorCode;
extern const int kQNDnsInvalidParamCode;
extern const int kQNDnsResponseBadTypeCode;
extern const int kQNDnsResponseBadClassCode;
extern const int kQNDnsResponseFormatCode;
#define kQNDnsErrorDomain @"qiniu.dns"
@interface QNDnsError : NSObject
+ (NSError *)error:(int)code desc:(NSString *)desc;
@end
#define kQNDnsMethodError(description) [QNDnsError error:kQNDnsMethodErrorCode desc:description]
#define kQNDnsInvalidParamError(description) [QNDnsError error:kQNDnsInvalidParamCode desc:description]
#define kQNDnsResponseBadTypeError(description) [QNDnsError error:kQNDnsResponseBadTypeCode desc:description]
#define kQNDnsResponseBadClassError(description) [QNDnsError error:kQNDnsResponseBadClassCode desc:description]
#define kQNDnsResponseFormatError(description) [QNDnsError error:kQNDnsResponseFormatCode desc:description]
NS_ASSUME_NONNULL_END

View File

@@ -0,0 +1,27 @@
//
// QNDnsError.m
// Doh
//
// Created by yangsen on 2021/7/20.
//
#import "QNDnsError.h"
const int kQNDomainHijackingCode = -7001;
const int kQNDomainNotOwnCode = -7002;
const int kQNDomainSeverError = -7003;
const int kQNDnsMethodErrorCode = -7010;
const int kQNDnsInvalidParamCode = -7021;
const int kQNDnsResponseBadTypeCode = -7022;
const int kQNDnsResponseBadClassCode = -7023;
const int kQNDnsResponseFormatCode = -7024;
@implementation QNDnsError
+ (NSError *)error:(int)code desc:(NSString *)desc {
return [NSError errorWithDomain:kQNDnsErrorDomain code:code userInfo:@{@"user_info" : desc ?: @"nil"}];
}
@end

View File

@@ -0,0 +1,174 @@
//
// QNDnsManager.h
// HappyDNS
//
// Created by bailong on 15/6/23.
// Copyright (c) 2015年 Qiniu Cloud Storage. All rights reserved.
//
#import "QNRecord.h"
@class QNNetworkInfo;
@class QNDomain;
/**
* getaddrinfo 回调上层的函数
*
* @param host 请求的域名
* @return ip 列表
*/
typedef NSArray<NSString *> * (^QNGetAddrInfoCallback)(NSString *host);
/**
* ip status 回调上层的函数
*
* @param ip 请求的IP
* @param code 错误码
* @param ms 消耗时间
*/
typedef void (^QNIpStatusCallback)(NSString *ip, int code, int ms);
/**
* 外部 Record 排序接口
*/
@protocol QNRecordSorter <NSObject>
/**
* 排序方法
*
* @param ips 传入的IP列表
*
* @return 返回排序好的IP 列表
*/
- (NSArray<QNRecord *> *)sort:(NSArray<QNRecord *> *)ips;
@end
/**
* DNS请求客户端集成了cache管理
*/
@interface QNDnsManager : NSObject
/// 查询失败时抛出错误信息回调
@property(nonatomic, copy)void(^queryErrorHandler)(NSError *error, NSString *host);
/**
* 解析域名
*
* @param domain 域名
*
* @return QNRecord列表 QNRecord.value即为host
*/
- (NSArray <QNRecord *> *)queryRecords:(NSString *)domain;
/**
* 解析域名使用Domain对象进行详细约定
*
* @param domain 配置了一些domain 参数的 domain 对象
*
* @return IP 列表
*/
- (NSArray <QNRecord *> *)queryRecordsWithDomain:(QNDomain *)domain;
/**
* 通知网络发生变化
*
* @param netInfo 网络信息
*/
- (void)onNetworkChange:(QNNetworkInfo *)netInfo;
/**
* Dns client 初始化
*
* @param resolvers 解析服务器列表
* @param netInfo 当前网络信息
*
* @return DnsManager
*/
- (instancetype)init:(NSArray *)resolvers networkInfo:(QNNetworkInfo *)netInfo;
/**
* Dns client 初始化
*
* @param resolvers 解析服务器列表
* @param netInfo 当前网络信息
* @param sorter 外部排序函数
*
* @return DnsManager
*/
- (instancetype)init:(NSArray *)resolvers networkInfo:(QNNetworkInfo *)netInfo sorter:(id<QNRecordSorter>)sorter;
/**
* 内置 Hosts 解析
*
* @param domain 域名
* @param ipv4 对应IPv4 ip
*
* @return 当前Dnsmanager, 为了链式调用
*/
- (instancetype)putHosts:(NSString *)domain ipv4:(NSString *)ipv4;
/**
* 内置 Hosts 解析
*
* @param domain 域名
* @param ip 对应IP
* @param type ip 类别kQNTypeA / kQNTypeAAAA
* @param provider 网络运营商
*
* @return 当前Dnsmanager, 为了链式调用
*/
- (instancetype)putHosts:(NSString *)domain ip:(NSString *)ip type:(int)type provider:(int)provider;
/**
* 内置 Hosts 解析
*
* @param domain 域名
* @param record 对应 record 记录
* @param provider 网络运营商
*
* @return 当前Dnsmanager, 为了链式调用
*/
- (instancetype)putHosts:(NSString *)domain record:(QNRecord *)record provider:(int)provider;
/**
* 设置底层 getaddrinfo 使用的回调
*
* @param block 回调的代码块
*/
+ (void)setGetAddrInfoBlock:(QNGetAddrInfoCallback)block;
/**
* 设置底层 getaddrinfo 回调使用的dnsmanager
*
* @param dns 回调用的dnsmanager
*/
+ (void)setDnsManagerForGetAddrInfo:(QNDnsManager *)dns;
/**
* 设置底层 业务统计 如connect 回调使用的Callback
*
* @param block 回调返回该IP状态
*/
+ (void)setIpStatusCallback:(QNIpStatusCallback)block;
/**
* 根据时区判断是否要设置httpDns
*/
+ (BOOL)needHttpDns;
@end
/**
* DnsManager 的 URL 辅助类
*/
@interface QNDnsManager (NSURL)
/**
* 使用URL 进行请求
*
* @param url 请求的Url
*
* @return 返回IP 替换过的url
*/
- (NSURL *)queryAndReplaceWithIP:(NSURL *)url;
@end

View File

@@ -0,0 +1,322 @@
//
// QNDnsManager.m
// HappyDNS
//
// Created by bailong on 15/6/23.
// Copyright (c) 2015 Qiniu Cloud Storage. All rights reserved.
//
#import "QNDnsManager.h"
#import "QNDomain.h"
#import "QNHosts.h"
#import "QNIP.h"
#import "QNLruCache.h"
#import "QNNetworkInfo.h"
#import "QNRecord.h"
#import "QNResolverDelegate.h"
#include "QNGetAddrInfo.h"
@interface QNDnsManager ()
@property (nonatomic, strong) QNLruCache *cache;
@property (atomic) QNNetworkInfo *curNetwork;
@property (nonatomic) NSArray *resolvers;
@property (atomic) UInt32 resolverStatus;
@property (nonatomic, strong) QNHosts *hosts;
@property (nonatomic, strong) id<QNRecordSorter> sorter;
@end
//static inline BOOL bits_isSet(UInt32 v, int index) {
// return (v & (1 << index)) != 0;
//}
static inline UInt32 bits_set(UInt32 v, int bitIndex) {
return v |= (1 << bitIndex);
}
static inline UInt32 bits_leadingZeros(UInt32 x) {
UInt32 y;
int n = 32;
y = x >> 16;
if (y != 0) {
n = n - 16;
x = y;
}
y = x >> 8;
if (y != 0) {
n = n - 8;
x = y;
}
y = x >> 4;
if (y != 0) {
n = n - 4;
x = y;
}
y = x >> 2;
if (y != 0) {
n = n - 2;
x = y;
}
y = x >> 1;
if (y != 0) {
return n - 2;
}
return n - x;
}
static NSMutableArray *trimCname(NSArray *records) {
NSMutableArray *array = [[NSMutableArray alloc] init];
for (QNRecord *r in records) {
if (r.type == kQNTypeA || r.type == kQNTypeAAAA) {
[array addObject:r];
}
}
return array;
}
static NSArray<NSString *> *records2Ips(NSArray<QNRecord *> *records) {
NSMutableArray *array = [[NSMutableArray alloc] init];
for (QNRecord *r in records) {
if (r.value && r.value.length > 0) {
[array addObject:r.value];
}
}
return [array copy];
}
static NSArray<QNRecord *> * filterInvalidRecords(NSArray *records) {
NSMutableArray *array = [[NSMutableArray alloc] init];
long long timestamp = [[NSDate date] timeIntervalSince1970];
for (QNRecord *r in records) {
if (r.value && r.value.length > 0 && ![r expired:timestamp]) {
[array addObject:r];
}
}
return [array copy];
}
@interface DummySorter : NSObject <QNRecordSorter>
@end
@implementation DummySorter
//sorted already
- (NSArray *)sort:(NSArray *)ips {
return ips;
}
@end
@implementation QNDnsManager
- (NSArray <QNRecord *> *)queryRecords:(NSString *)domain {
return [self queryRecordsWithDomain:[[QNDomain alloc] init:domain]];
}
- (NSArray <QNRecord *> *)queryRecordsWithDomain:(QNDomain *)domain{
if (domain == nil) {
return nil;
}
if ([QNIP mayBeIpV4:domain.domain]) {
QNRecord *record = [[QNRecord alloc] init:domain.domain ttl:kQNRecordForeverTTL type:kQNTypeA source:QNRecordSourceUnknown];
return [NSArray arrayWithObject:record];
}
NSArray<QNRecord *> *records = [self queryInternalWithDomain:domain];
return [_sorter sort:records];
}
- (NSArray <QNRecord *> *)queryInternalWithDomain:(QNDomain *)domain {
if (domain.hostsFirst) {
NSArray <QNRecord *> *result = [_hosts query:domain networkInfo:_curNetwork];
result = filterInvalidRecords(result);
if (result.count > 0) {
return [result copy];
}
}
if ([_curNetwork isEqualToInfo:[QNNetworkInfo normal]] && [QNNetworkInfo isNetworkChanged]) {
@synchronized(_cache) {
[_cache removeAllObjects];
}
_resolverStatus = 0;
} else {
@synchronized(_cache) {
NSArray *result = [_cache objectForKey:domain.domain];
result = filterInvalidRecords(result);
if (result.count > 0) {
return [result copy];
}
}
}
NSArray *records = nil;
NSError *error = nil;
int firstOk = 32 - bits_leadingZeros(_resolverStatus);
for (int i = 0; i < _resolvers.count; i++) {
int pos = (firstOk + i) % _resolvers.count;
id<QNResolverDelegate> resolver = [_resolvers objectAtIndex:pos];
QNNetworkInfo *previousNetwork = _curNetwork;
NSString *previousIp = [QNNetworkInfo getIp];
records = [resolver query:domain networkInfo:previousNetwork error:&error];
if (error != nil) {
NSError *tmp = error;
error = nil;
if (tmp.code == kQNDomainNotOwnCode) {
continue;
}
if (self.queryErrorHandler) {
self.queryErrorHandler(error, domain.domain);
}
}
if (records == nil || records.count == 0) {
if (_curNetwork == previousNetwork && [previousIp isEqualToString:[QNNetworkInfo getIp]]) {
_resolverStatus = bits_set(_resolverStatus, pos);
}
} else {
NSMutableArray *result = trimCname(records);
if (_curNetwork == previousNetwork && [previousIp isEqualToString:[QNNetworkInfo getIp]]) {
@synchronized(_cache) {
[_cache setObject:[result copy] forKey:domain.domain];
}
}
return [result copy];
}
}
if (!domain.hostsFirst) {
return [_hosts query:domain networkInfo:_curNetwork];
}
return nil;
}
- (instancetype)init:(NSArray *)resolvers networkInfo:(QNNetworkInfo *)netInfo {
return [self init:resolvers networkInfo:netInfo sorter:nil];
}
- (instancetype)init:(NSArray *)resolvers networkInfo:(QNNetworkInfo *)netInfo sorter:(id<QNRecordSorter>)sorter {
if (self = [super init]) {
_cache = [[QNLruCache alloc] init:1024];
_curNetwork = netInfo;
_resolvers = [[NSArray alloc] initWithArray:resolvers];
_hosts = [[QNHosts alloc] init];
if (sorter == nil) {
_sorter = [[DummySorter alloc] init];
} else {
_sorter = sorter;
}
}
return self;
}
- (void)onNetworkChange:(QNNetworkInfo *)netInfo {
@synchronized(_cache) {
[_cache removeAllObjects];
}
_curNetwork = netInfo;
}
- (instancetype)putHosts:(NSString *)domain ipv4:(NSString *)ipv4 {
return [self putHosts:domain ip:ipv4 type:kQNTypeA provider:kQNISP_GENERAL];
}
- (instancetype)putHosts:(NSString *)domain ip:(NSString *)ip type:(int)type provider:(int)provider {
return [self putHosts:domain record:[[QNRecord alloc] init:ip ttl:kQNRecordForeverTTL type:type source:QNRecordSourceCustom] provider:provider];
}
- (instancetype)putHosts:(NSString *)domain record:(QNRecord *)record provider:(int)provider {
QNRecord *recordNew = [[QNRecord alloc] init:record.value ttl:record.ttl type:record.type timeStamp:record.timeStamp server:record.server source:QNRecordSourceCustom];
[_hosts put:domain record:recordNew provider:provider];
return self;
}
- (NSURL *)queryAndReplaceWithIP:(NSURL *)url {
NSURLComponents *urlComponents = [[NSURLComponents alloc] initWithURL:url resolvingAgainstBaseURL:YES];
if (!urlComponents) {
return nil;
}
NSString *host = urlComponents.host;
NSArray<QNRecord *> *records = [self queryRecords:host];
NSURL *URL = nil;
if (records && records.firstObject) {
urlComponents.host = [QNIP ipHost:records.firstObject.value];
}
URL = urlComponents.URL;
return URL;
}
static QNGetAddrInfoCallback getAddrInfoCallback = nil;
static qn_ips_ret *dns_callback_internal(const char *host) {
if (getAddrInfoCallback == nil) {
return NULL;
}
NSString *s = [[NSString alloc] initWithUTF8String:host];
if (s == nil) {
return NULL;
}
NSArray *ips = getAddrInfoCallback(s);
if (ips == nil) {
return NULL;
}
qn_ips_ret *ret = calloc(sizeof(char *), ips.count + 1);
for (int i = 0; i < ips.count; i++) {
NSString *ip = ips[i];
char *ip2 = strdup([ip cStringUsingEncoding:NSUTF8StringEncoding]);
ret->ips[i] = ip2;
}
return ret;
}
static qn_ips_ret *dns_callback(const char *host) {
qn_ips_ret *ret = dns_callback_internal(host);
if (ret == NULL) {
//only for compatible
qn_ips_ret *ret = calloc(sizeof(char *), 2);
ret->ips[0] = strdup(host);
}
return ret;
}
static QNIpStatusCallback ipStatusCallback = nil;
static void ip_status_callback(const char *ip, int code, int time_ms) {
if (ipStatusCallback == nil) {
return;
}
NSString *s = [[NSString alloc] initWithUTF8String:ip];
if (s == nil) {
return;
}
ipStatusCallback(s, code, time_ms);
}
+ (void)setGetAddrInfoBlock:(QNGetAddrInfoCallback)block {
if ([QNIP isIpV6FullySupported] || ![QNIP isV6]) {
getAddrInfoCallback = block;
qn_set_dns_callback(dns_callback);
}
}
+ (void)setDnsManagerForGetAddrInfo:(QNDnsManager *)dns {
[QNDnsManager setGetAddrInfoBlock:^NSArray<NSString *> *(NSString *host) {
NSArray *records = [dns queryRecords:host];
return records2Ips(records);
}];
}
+ (void)setIpStatusCallback:(QNIpStatusCallback)block {
ipStatusCallback = block;
qn_set_ip_report_callback(ip_status_callback);
}
+ (BOOL)needHttpDns {
NSTimeZone *timeZone = [NSTimeZone localTimeZone];
NSString *tzName = [timeZone name];
return [tzName isEqual:@"Asia/Shanghai"] || [tzName isEqual:@"Asia/Chongqing"] || [tzName isEqual:@"Asia/Harbin"] || [tzName isEqual:@"Asia/Urumqi"];
}
@end

27
Pods/HappyDNS/HappyDNS/Common/QNDomain.h generated Normal file
View File

@@ -0,0 +1,27 @@
//
// QNDomain.h
// HappyDNS
//
// Created by bailong on 15/6/23.
// Copyright (c) 2015年 Qiniu Cloud Storage. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface QNDomain : NSObject
@property (nonatomic, strong, readonly) NSString *domain;
// 用来判断劫持
@property (nonatomic, readonly) BOOL hasCname;
// 用来判断劫持
@property (nonatomic, readonly) int maxTtl;
@property (nonatomic, readonly) BOOL hostsFirst;
- (instancetype)init:(NSString *)domain;
- (instancetype)init:(NSString *)domain hostsFirst:(BOOL)hostsFirst hasCname:(BOOL)hasCname;
- (instancetype)init:(NSString *)domain hostsFirst:(BOOL)hostsFirst hasCname:(BOOL)hasCname maxTtl:(int)maxTtl;
@end

30
Pods/HappyDNS/HappyDNS/Common/QNDomain.m generated Normal file
View File

@@ -0,0 +1,30 @@
//
// QNDomain.m
// HappyDNS
//
// Created by bailong on 15/6/23.
// Copyright (c) 2015 Qiniu Cloud Storage. All rights reserved.
//
#import "QNDomain.h"
@implementation QNDomain
- (instancetype)init:(NSString *)domain {
return [self init:domain hostsFirst:NO hasCname:NO maxTtl:0];
}
- (instancetype)init:(NSString *)domain hostsFirst:(BOOL)hostsFirst hasCname:(BOOL)hasCname {
return [self init:domain hostsFirst:hostsFirst hasCname:hasCname maxTtl:0];
}
- (instancetype)init:(NSString *)domain hostsFirst:(BOOL)hostsFirst hasCname:(BOOL)hasCname maxTtl:(int)maxTtl {
if (self = [super init]) {
_domain = domain;
_hasCname = hasCname;
_maxTtl = maxTtl;
_hostsFirst = hostsFirst;
}
return self;
}
@end

View File

@@ -0,0 +1,23 @@
//
// QNLruCache.h
// HappyDNS
//
// Created by bailong on 16/7/5.
// Copyright © 2016年 Qiniu Cloud Storage. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface QNLruCache : NSObject
- (instancetype)init:(NSUInteger)limit;
- (void)removeAllObjects;
- (void)removeObjectForKey:(NSString *)key;
- (id)objectForKey:(NSString *)key;
- (void)setObject:(id)obj forKey:(NSString *)key;
@end

View File

@@ -0,0 +1,90 @@
//
// QNLruCache.m
// HappyDNS
//
// Created by bailong on 16/7/5.
// Copyright © 2016 Qiniu Cloud Storage. All rights reserved.
//
#import "QNLruCache.h"
@interface QNLruCache ()
@property (nonatomic, readonly) NSUInteger limit;
@property (nonatomic, readonly) NSMutableDictionary* cache;
@property (nonatomic, readonly) NSMutableArray* list;
@end
@interface _QNElement : NSObject
@property (nonatomic, readonly, strong) NSString* key;
@property (nonatomic, strong) id obj;
- (instancetype)initObject:(id)obj forKey:(NSString*)key;
@end
@implementation _QNElement
- (instancetype)initObject:(id)obj forKey:(NSString*)key {
if (self = [super init]) {
_key = key;
_obj = obj;
}
return self;
}
@end
@implementation QNLruCache
- (instancetype)init:(NSUInteger)limit {
if (self = [super init]) {
_limit = limit;
_cache = [NSMutableDictionary new];
_list = [NSMutableArray new];
}
return self;
}
- (void)removeAllObjects {
[_cache removeAllObjects];
[_list removeAllObjects];
}
- (void)removeObjectForKey:(NSString*)key {
_QNElement* obj = [_cache objectForKey:key];
if (obj == nil) {
return;
}
[_cache removeObjectForKey:key];
[_list removeObjectIdenticalTo:obj];
}
- (id)objectForKey:(NSString*)key {
_QNElement* obj = [_cache objectForKey:key];
if (obj != nil) {
[_list removeObjectIdenticalTo:obj];
[_list insertObject:obj atIndex:0];
}
return obj.obj;
}
- (void)setObject:(id)obj forKey:(NSString*)key {
_QNElement* old = [_cache objectForKey:key];
if (old) {
old.obj = obj;
[_list removeObjectIdenticalTo:old];
[_list insertObject:old atIndex:0];
return;
} else if (_list.count == _limit) {
old = [_list lastObject];
[_list removeLastObject];
[_cache removeObjectForKey:old.key];
}
_QNElement* newElement = [[_QNElement alloc] initObject:obj forKey:key];
[_cache setObject:newElement forKey:key];
[_list insertObject:newElement atIndex:0];
}
@end

View File

@@ -0,0 +1,42 @@
//
// QNNetworkInfo.h
// HappyDNS
//
// Created by bailong on 15/6/25.
// Copyright (c) 2015年 Qiniu Cloud Storage. All rights reserved.
//
#import <Foundation/Foundation.h>
extern const int kQNNO_NETWORK;
extern const int kQNWIFI;
extern const int kQNMOBILE;
extern const int kQNISP_GENERAL;
extern const int kQNISP_CTC;
extern const int kQNISP_DIANXIN;
extern const int kQNISP_CNC;
extern const int kQNISP_LIANTONG;
extern const int kQNISP_CMCC;
extern const int kQNISP_YIDONG;
extern const int kQNISP_OTHER;
@interface QNNetworkInfo : NSObject
@property (nonatomic, readonly) int networkConnection;
@property (nonatomic, readonly) int provider;
- (instancetype)init:(int)connecton provider:(int)provider;
- (BOOL)isEqual:(id)other;
- (BOOL)isEqualToInfo:(QNNetworkInfo *)info;
+ (instancetype)noNet;
+ (instancetype)normal;
+ (BOOL)isNetworkChanged;
+ (NSString *)getIp;
@end

View File

@@ -0,0 +1,86 @@
//
// QNNetworkInfo.m
// HappyDNS
//
// Created by bailong on 15/6/25.
// Copyright (c) 2015 Qiniu Cloud Storage. All rights reserved.
//
#import <arpa/inet.h>
#include <fcntl.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <unistd.h>
#import "QNIP.h"
#import "QNNetworkInfo.h"
const int kQNNO_NETWORK = -1;
const int kQNWIFI = 1;
const int kQNMOBILE = 2;
const int kQNISP_GENERAL = 0;
const int kQNISP_CTC = 1;
const int kQNISP_DIANXIN = kQNISP_CTC;
const int kQNISP_CNC = 2;
const int kQNISP_LIANTONG = kQNISP_CNC;
const int kQNISP_CMCC = 3;
const int kQNISP_YIDONG = kQNISP_CMCC;
const int kQNISP_OTHER = 999;
#define IPLength 64
static char previousIp[IPLength] = {0};
static NSString *lock = @"";
@implementation QNNetworkInfo
- (instancetype)init:(int)connecton provider:(int)provider {
if (self = [super init]) {
_networkConnection = connecton;
_provider = provider;
}
return self;
}
+ (instancetype)noNet {
return [[QNNetworkInfo alloc] init:kQNNO_NETWORK provider:kQNISP_GENERAL];
}
+ (instancetype)normal {
return [[QNNetworkInfo alloc] init:kQNISP_GENERAL provider:kQNISP_GENERAL];
}
- (BOOL)isEqualToInfo:(QNNetworkInfo *)info {
if (self == info)
return YES;
return self.provider == info.provider && self.networkConnection == info.networkConnection;
}
- (BOOL)isEqual:(id)other {
if (other == self)
return YES;
if (!other || ![other isKindOfClass:[self class]])
return NO;
return [self isEqualToInfo:other];
}
+ (BOOL)isNetworkChanged {
@synchronized(lock) {
char local[IPLength] = {0};
int err = qn_localIp(local, sizeof(local));
if (err != 0) {
return YES;
}
if (memcmp(previousIp, local, sizeof(local)) != 0) {
memcpy(previousIp, local, sizeof(local));
return YES;
}
return NO;
}
}
+ (NSString *)getIp {
return [QNIP local];
}
@end

69
Pods/HappyDNS/HappyDNS/Common/QNRecord.h generated Normal file
View File

@@ -0,0 +1,69 @@
//
// QNRecord.h
// HappyDNS
//
// Created by bailong on 15/6/23.
// Copyright (c) 2015年 Qiniu Cloud Storage. All rights reserved.
//
#import <Foundation/Foundation.h>
/**
* A 记录
*/
extern const int kQNTypeA;
/**
* AAAA 记录
*/
extern const int kQNTypeAAAA;
/**
* Cname 记录
*/
extern const int kQNTypeCname;
/**
* Txt 记录
*/
extern const int kQNTypeTXT;
/**
* 永久有效的 ttl
*/
extern const int kQNRecordForeverTTL;
typedef NS_ENUM(NSUInteger, QNRecordSource) {
QNRecordSourceUnknown,
QNRecordSourceCustom,
QNRecordSourceDnspodEnterprise,
QNRecordSourceSystem,
QNRecordSourceUdp,
QNRecordSourceDoh,
};
@interface QNRecord : NSObject
@property (nonatomic, copy, readonly) NSString *value;
@property (nonatomic, copy, readonly) NSString *server;
@property (nonatomic, readonly) int ttl;
@property (nonatomic, readonly) int type;
@property (nonatomic, readonly) long long timeStamp;
@property (nonatomic, readonly) QNRecordSource source;
- (instancetype)init:(NSString *)value
ttl:(int)ttl
type:(int)type
source:(QNRecordSource)source;
- (instancetype)init:(NSString *)value
ttl:(int)ttl
type:(int)type
timeStamp:(long long)timeStamp
server:(NSString *)server
source:(QNRecordSource)source;
- (BOOL)expired:(long long)time;
@end

60
Pods/HappyDNS/HappyDNS/Common/QNRecord.m generated Normal file
View File

@@ -0,0 +1,60 @@
//
// QNRecord.m
// HappyDNS
//
// Created by bailong on 15/6/23.
// Copyright (c) 2015 Qiniu Cloud Storage. All rights reserved.
//
#import "QNRecord.h"
const int kQNTypeA = 1;
const int kQNTypeAAAA = 28;
const int kQNTypeCname = 5;
const int kQNTypeTXT = 16;
const int kQNRecordForeverTTL = -1;
@implementation QNRecord
- (instancetype)init:(NSString *)value
ttl:(int)ttl
type:(int)type
source:(QNRecordSource)source {
if (self = [super init]) {
_value = value;
_type = type;
_ttl = ttl;
_source = source;
_timeStamp = [[NSDate date] timeIntervalSince1970];
}
return self;
}
- (instancetype)init:(NSString *)value
ttl:(int)ttl
type:(int)type
timeStamp:(long long)timeStamp
server:(NSString *)server
source:(QNRecordSource)source {
if (self = [super init]) {
_value = value;
_type = type;
_ttl = ttl;
_server = server;
_source = source;
_timeStamp = timeStamp;
}
return self;
}
- (BOOL)expired:(long long)time {
if (_ttl == kQNRecordForeverTTL) {
return false;
}
return time > _timeStamp + _ttl;
}
- (NSString *)description {
return [NSString stringWithFormat:@"value:%@, ttl:%d, timestamp:%lld, type:%d server:%@ source:%lu", _value, _ttl, _timeStamp, _type, _server, (unsigned long)_source];
}
@end

View File

@@ -0,0 +1,19 @@
//
// QNResolverDelegate.h
// HappyDNS
//
// Created by bailong on 15/6/23.
// Copyright (c) 2015年 Qiniu Cloud Storage. All rights reserved.
//
#import "QNDnsError.h"
#define QN_DNS_DEFAULT_TIMEOUT 20 //seconds
@class QNDomain;
@class QNNetworkInfo;
@protocol QNResolverDelegate <NSObject>
- (NSArray *)query:(QNDomain *)domain networkInfo:(QNNetworkInfo *)netInfo error:(NSError **)error;
@end