use curl;
use auth::EdgeGridAuth;
use auth::RequestVerb::*;
use url::percent_encoding as pe;
use rustc_serialize::json;
use std::borrow::Borrow;
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct LocationsResponse {
locations: Option<Vec<String>>,
errorString: Option<String>,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct DigRecordData {
domain: String,
ttl: usize,
recordClass: String,
recordType: String,
preferenceValues: Option<String>,
value: String,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct DigData {
hostname: Option<String>,
queryType: Option<String>,
answerSection: Option<Vec<DigRecordData>>,
authoritySection: Option<Vec<DigRecordData>>,
result: Option<String>,
errorString: Option<String>,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct DigResponse {
dig: DigData,
}
#[derive(Debug)]
pub enum DigQueryType {
A,
MX,
NS
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct MtrHop {
num: String,
host: String,
loss: String,
sent: String,
last: String,
avg: String,
best: String,
worst: String,
stDev: String,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct MtrData {
source: Option<String>,
destination: Option<String>,
host: Option<String>,
packetLoss: Option<String>,
avgLatency: Option<String>,
analysis: Option<String>,
errorString: Option<String>,
hops: Option<Vec<MtrHop>>
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct MtrResponse {
mtr: MtrData,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct ArlResponse {
typeCode: Option<String>,
originServer: Option<String>,
cpCode: Option<String>,
serialNumber: Option<String>,
ttl: Option<String>,
pragma: Option<String>,
cacheControl: Option<String>,
errorString: Option<String>,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct LogLine {
logLine: Option<String>,
fields: Option<String>,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct ErrorData {
url: Option<String>,
httpResponseCode: Option<usize>,
dateTime: Option<String>,
epochTime: Option<String>,
clientIP: Option<String>,
serverIP: Option<String>,
originHostname: Option<String>,
originIP: Option<String>,
userAgent: Option<String>,
requestMethod: Option<String>,
reasonForFailure: Option<String>,
logs: Option<Vec<LogLine>>,
errorString: Option<String>,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct ErrorTranslateResponse {
errorTranslator: ErrorData
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct IPGeoLocationData {
clientIp: Option<String>,
countryCode: Option<String>,
regionCode: Option<String>,
city: Option<String>,
dma: Option<String>,
msa: Option<String>,
pmsa: Option<String>,
areaCode: Option<String>,
latitude: Option<String>,
longitude: Option<String>,
county: Option<String>,
continent: Option<String>,
fips: Option<String>,
timeZone: Option<String>,
network: Option<String>,
networkType: Option<String>,
zipCode: Option<String>,
throughput: Option<String>,
asNum: Option<String>,
errorString: Option<String>,
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct IPGeoLocationResponse {
ipGeoLocation: IPGeoLocationData
}
#[derive(Debug, RustcDecodable)]
#[allow(non_snake_case)]
pub struct VerifyIPCDNResponse {
isCdnIP: Option<String>,
errorString: Option<String>,
ip: Option<String>,
}
pub fn locations(egr: &EdgeGridAuth) -> Result<LocationsResponse, ::ApiError> {
let mut url = String::from(egr.baseurl());
let relurl = String::from("/diagnostic-tools/v1/locations");
url.push_str(&relurl[..]);
url = pe::utf8_percent_encode(&url[..], pe::QUERY_ENCODE_SET);
let header = try!(egr.auth_header(GET, &relurl[..], None));
debug!("URL: {}", url);
let resp = try!(curl::http::handle()
.timeout(egr.timeout())
.get(&url[..])
.header("Authorization", &header[..])
.exec()
);
let body = String::from_utf8_lossy(resp.get_body());
debug!("Status: {}", resp.get_code());
debug!("Body: {}", body);
match resp.get_code() {
200 => {
let jsonresp: LocationsResponse = try!(json::decode(&body));
Ok(jsonresp)
},
_ => {
let json_err: ::JSONError = try!(json::decode(&body));
Err(::ApiError{
json_err: json_err,
body: String::from(body.borrow())
})
}
}
}
pub fn dig(
egr: &EdgeGridAuth,
host: &str,
loc: &str,
query_type: DigQueryType
) -> Result<DigResponse, ::ApiError> {
let mut url = String::from(egr.baseurl());
let mut relurl = String::from("/diagnostic-tools/v1/dig");
relurl.push_str("?");
relurl.push_str(&format!("hostname={}&", host)[..]);
relurl.push_str(&format!("location={}&", loc)[..]);
relurl.push_str(&format!("queryType={:?}", query_type)[..]);
relurl = pe::utf8_percent_encode(&relurl[..], pe::QUERY_ENCODE_SET);
url.push_str(&relurl[..]);
let header = try!(egr.auth_header(GET, &relurl[..], None));
debug!("URL: {}", url);
let resp = try!(curl::http::handle()
.timeout(egr.timeout())
.get(&url[..])
.header("Authorization", &header[..])
.exec()
);
let body = String::from_utf8_lossy(resp.get_body());
debug!("Status: {}", resp.get_code());
debug!("Body: {}", body);
match resp.get_code() {
200 => {
let jsonresp: DigResponse = try!(json::decode(&body));
Ok(jsonresp)
},
_ => {
let json_err: ::JSONError = try!(json::decode(&body));
Err(::ApiError{
json_err: json_err,
body: String::from(body.borrow())
})
}
}
}
pub fn mtr(
egr: &EdgeGridAuth,
dest: &str,
loc: &str
) -> Result<MtrResponse, ::ApiError> {
let mut url = String::from(egr.baseurl());
let mut relurl = String::from("/diagnostic-tools/v1/mtr");
relurl.push_str("?");
relurl.push_str(&format!("destinationDomain={}&", dest)[..]);
relurl.push_str(&format!("location={}&", loc)[..]);
relurl = pe::utf8_percent_encode(&relurl[..], pe::QUERY_ENCODE_SET);
url.push_str(&relurl[..]);
let header = try!(egr.auth_header(GET, &relurl[..], None));
debug!("URL: {}", url);
let resp = try!(curl::http::handle()
.timeout(egr.timeout())
.get(&url[..])
.header("Authorization", &header[..])
.exec()
);
let body = String::from_utf8_lossy(resp.get_body());
debug!("Status: {}", resp.get_code());
debug!("Body: {}", body);
match resp.get_code() {
200 => {
let jsonresp: MtrResponse = try!(json::decode(&body));
Ok(jsonresp)
},
_ => {
let json_err: ::JSONError = try!(json::decode(&body));
Err(::ApiError{
json_err: json_err,
body: String::from(body.borrow())
})
}
}
}
pub fn translate(
egr: &EdgeGridAuth,
host: &str
) -> Result<ArlResponse, ::ApiError> {
let mut url = String::from(egr.baseurl());
let mut relurl = String::from("/diagnostic-tools/v1/akamaitranslator");
relurl.push_str("?");
relurl.push_str(&format!("hostname={}&", host)[..]);
relurl = pe::utf8_percent_encode(&relurl[..], pe::QUERY_ENCODE_SET);
url.push_str(&relurl[..]);
let header = try!(egr.auth_header(GET, &relurl[..], None));
debug!("URL: {}", url);
let resp = try!(curl::http::handle()
.timeout(egr.timeout())
.get(&url[..])
.header("Authorization", &header[..])
.exec()
);
let body = String::from_utf8_lossy(resp.get_body());
debug!("Status: {}", resp.get_code());
debug!("Body: {}", body);
match resp.get_code() {
200 => {
let jsonresp: ArlResponse = try!(json::decode(&body));
Ok(jsonresp)
},
_ => {
let json_err: ::JSONError = try!(json::decode(&body));
Err(::ApiError{
json_err: json_err,
body: String::from(body.borrow())
})
}
}
}
pub fn error_translate(
egr: &EdgeGridAuth,
error_code: &str
) -> Result<ErrorTranslateResponse, ::ApiError> {
let mut url = String::from(egr.baseurl());
let mut relurl = String::from("/diagnostic-tools/v1/errortranslator");
relurl.push_str("?");
relurl.push_str(&format!("errorCode={}&", error_code)[..]);
relurl = pe::utf8_percent_encode(&relurl[..], pe::QUERY_ENCODE_SET);
url.push_str(&relurl[..]);
let header = try!(egr.auth_header(GET, &relurl[..], None));
debug!("URL: {}", url);
let resp = try!(curl::http::handle()
.timeout(egr.timeout())
.get(&url[..])
.header("Authorization", &header[..])
.exec()
);
let body = String::from_utf8_lossy(resp.get_body());
debug!("Status: {}", resp.get_code());
debug!("Body: {}", body);
match resp.get_code() {
200 => {
let jsonresp: ErrorTranslateResponse = try!(json::decode(&body));
Ok(jsonresp)
},
_ => {
let json_err: ::JSONError = try!(json::decode(&body));
Err(::ApiError{
json_err: json_err,
body: String::from(body.borrow())
})
}
}
}
pub fn geolocate(
egr: &EdgeGridAuth,
ip: &str
) -> Result<IPGeoLocationResponse, ::ApiError> {
let mut url = String::from(egr.baseurl());
let mut relurl = String::from("/diagnostic-tools/v1/ipgeolocator");
relurl.push_str("?");
relurl.push_str(&format!("ip={}&", ip)[..]);
relurl = pe::utf8_percent_encode(&relurl[..], pe::QUERY_ENCODE_SET);
url.push_str(&relurl[..]);
let header = try!(egr.auth_header(GET, &relurl[..], None));
debug!("URL: {}", url);
let resp = try!(curl::http::handle()
.timeout(egr.timeout())
.get(&url[..])
.header("Authorization", &header[..])
.exec()
);
let body = String::from_utf8_lossy(resp.get_body());
debug!("Status: {}", resp.get_code());
debug!("Body: {}", body);
match resp.get_code() {
200 => {
let jsonresp: IPGeoLocationResponse = try!(json::decode(&body));
Ok(jsonresp)
},
_ => {
let json_err: ::JSONError = try!(json::decode(&body));
Err(::ApiError{
json_err: json_err,
body: String::from(body.borrow())
})
}
}
}
pub fn verifycdnip(
egr: &EdgeGridAuth,
ip: &str
) -> Result<VerifyIPCDNResponse, ::ApiError> {
let mut url = String::from(egr.baseurl());
let mut relurl = String::from("/diagnostic-tools/v1/verifycdnip");
relurl.push_str("?");
relurl.push_str(&format!("ip={}&", ip)[..]);
relurl = pe::utf8_percent_encode(&relurl[..], pe::QUERY_ENCODE_SET);
url.push_str(&relurl[..]);
let header = try!(egr.auth_header(GET, &relurl[..], None));
debug!("URL: {}", url);
let resp = try!(curl::http::handle()
.timeout(egr.timeout())
.get(&url[..])
.header("Authorization", &header[..])
.exec()
);
let body = String::from_utf8_lossy(resp.get_body());
debug!("Status: {}", resp.get_code());
debug!("Body: {}", body);
match resp.get_code() {
200 => {
let jsonresp: VerifyIPCDNResponse = try!(json::decode(&body));
Ok(jsonresp)
},
_ => {
let json_err: ::JSONError = try!(json::decode(&body));
Err(::ApiError{
json_err: json_err,
body: String::from(body.borrow())
})
}
}
}