Unnamed
public text v1 · immutablepragma(lib, "ws2_32.lib");
import std.string, std.conv, std.stream;
import std.socket, std.socketstream;
class HTTP {
this(){
headers = "Accept: text/*" ~ NL;
headers ~= "User-Agent: DHTTPC/1.0" ~ NL;
}
this(char[] url){
this();
GET(url);
}
this(char[] url, char[][char[]] headers){
this();
foreach(char[] name, char[] value; headers){
setHeader(name, value);
}
GET(url);
}
~this(){
// ?
}
public{
void setHeader(char[] name, char[] value){
// Check if header already exists?
headers ~= name ~": " ~ value ~ NL;
}
char[] getHeaders(){
return headers;
}
bool GET(char[] url){
// Assumes response is 200 OK, can't handle redirects (should be
easily implemented if needed though)
// Parse URL
int i;
// Check for HTTP protocol in URL
i = std.string.find(url, "://");
if(i != -1){
if(icmp(url[0 .. i], "http"))
throw new Exception("URL Protocol is not HTTP.");
}else{
throw new Exception("URL has no protocol.");
}
// Remove anchor
i = std.string.find(url, '#');
if(i != -1)
url = url[0 .. i];
// Split URL into domain and URI
char[] domain;
i = std.string.find(url, '/');
if(i == -1){
domain = url;
url = "/";
}else{
domain = url[0 .. i];
url = url[i .. url.length];
}
// Find port
uint port;
i = std.string.find(domain, ':');
if(i == -1){
port = 80;
}else{
port = std.conv.toUshort(domain[i + 1 .. domain.length]);
domain = domain[0 .. i];
}
// Set HOST header
setHeader("Host", domain ~ ":" ~ std.string.toString(port));
// Open socket
sock = new Socket(cast(AddressFamily)(new InternetAddress(domain,
port)), SocketType.STREAM, ProtocolType.TCP);
sockstream = new SocketStream(sock);
// Do request
sockstream.writeString("GET " ~ url ~ " HTTP/1.1" ~ NL ~ headers ~
NL);
// Store headers
char[] line;
headers = "";
for(;;){
line = sockstream.readLine();
if(!line.length)
break;
headers ~= line;
}
// Store data
data = "";
while(!sockstream.eof()){
line = sockstream.readLine();
data ~= line;
}
// Close socket
sockstream.close();
return true;
}
bool GET(char[] url, char[][char[]] parameters){
char[] p = "?";
foreach(char[] n, char[] v; parameters){
if(p.length != 1)
p ~= "&";
p ~= n ~ "=" ~ v;
}
return GET(url ~ p);
}
bool POST(char[] url, char[][char[]] parameters){
char[] p = "?";
foreach(char[] n, char[] v; parameters){
if(p.length != 1)
p ~= "&";
p ~= n ~ "=" ~ v;
}
// Parse URL
int i;
// Check for HTTP protocol in URL
i = std.string.find(url, "://");
if(i != -1){
if(icmp(url[0 .. i], "http"))
throw new Exception("URL Protocol is not HTTP.");
}else{
throw new Exception("URL has no protocol.");
}
// Remove anchor
i = std.string.find(url, '#');
if(i != -1)
url = url[0 .. i];
// Split URL into domain and URI
char[] domain;
i = std.string.find(url, '/');
if(i == -1){
domain = url;
url = "/";
}else{
domain = url[0 .. i];
url = url[i .. url.length];
}
// Find port
uint port;
i = std.string.find(domain, ':');
if(i == -1){
port = 80;
}else{
port = std.conv.toUshort(domain[i + 1 .. domain.length]);
domain = domain[0 .. i];
}
// Set HOST header
setHeader("Host", domain ~ ":" ~ std.string.toString(port));
// Open socket
sock = new Socket(cast(AddressFamily)(new InternetAddress(domain,
port)), SocketType.STREAM, ProtocolType.TCP);
sockstream = new SocketStream(sock);
// Do request
sockstream.writeString("POST " ~ url ~ " HTTP/1.1" ~ NL ~ headers ~
NL ~ p ~ NL);
// Store headers
char[] line;
headers = "";
for(;;){
line = sockstream.readLine();
if(!line.length)
break;
headers ~= line;
}
// Store data
data = "";
while(!sockstream.eof()){
line = sockstream.readLine();
data ~= line;
}
// Close socket
sockstream.close();
return true;
}
char[] getData(){
return data;
}
}
private{
auto Socket sock;
Stream sockstream;
char[] data;
char[] headers;
const char[] NL = "\r\n";
}
}