Repository navigation
Expand file tree
/
Copy pathinet.h
More file actions
152 lines (142 loc) · 5.05 KB
/
Copy pathinet.h
File metadata and controls
152 lines (142 loc) · 5.05 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
// inet.h - WinINet
#pragma once
#define NOMINMAX
#include <windows.h>
#include <wininet.h>
#pragma comment(lib, "Wininet.lib")
#include <optional>
#include <string>
namespace Win {
class Hinternet {
private:
HINTERNET h;
protected:
Hinternet(HINTERNET h)
: h(h)
{ }
public:
Hinternet(const Hinternet&) = delete;
Hinternet& operator=(const Hinternet&) = delete;
Hinternet(Hinternet&& i)
: h(i.h)
{
i.h = INVALID_HANDLE_VALUE;
}
Hinternet& operator=(Hinternet&& i) = delete;
virtual ~Hinternet()
{
if (h != INVALID_HANDLE_VALUE)
InternetCloseHandle(h);
}
operator const HINTERNET() const
{
return h;
}
};
namespace Internet {
struct Open : public Hinternet {
Open(LPCTSTR agent = TEXT(""),
DWORD accessType = INTERNET_OPEN_TYPE_DIRECT,
LPCTSTR proxyName = NULL,
LPCTSTR proxyBypass = NULL,
DWORD flags = 0
) : Hinternet(InternetOpen(agent, accessType, proxyName, proxyBypass, flags))
{ }
};
// url or file
struct OpenResource : public Hinternet {
OpenResource(HINTERNET h)
: Hinternet(h)
{ }
template<class BUFFER = std::basic_string<TCHAR>, size_t BUFFER_SIZE = 1024>
std::optional<BUFFER> ReadFile()
{
TCHAR buf[BUFFER_SIZE];
DWORD n;
BUFFER buffer;
while (::InternetReadFile(*this, buf, BUFFER_SIZE, &n) && 0 != n) {
buffer.append(buf, n);
}
return buffer;
}
};
struct OpenUrl : public OpenResource {
OpenUrl(const Open& open,
LPCTSTR url,
LPCTSTR headers = TEXT(""),
DWORD headersLength = -1, // NULL terminated headers
DWORD flags = INTERNET_FLAG_EXISTING_CONNECT,
DWORD_PTR context = NULL
) : OpenResource(::InternetOpenUrl(open, url, headers, headersLength, flags, context))
{ }
};
struct Connect : public Hinternet {
Connect(const Open& h,
LPCTSTR serverName,
INTERNET_PORT serverPort = INTERNET_DEFAULT_HTTP_PORT,
LPCTSTR userName = NULL,
LPCTSTR password = NULL,
DWORD service = INTERNET_SERVICE_HTTP,
DWORD flags = 0,
DWORD_PTR context = NULL
) : Hinternet(InternetConnect(h, serverName, serverPort, userName, password, service, flags, context))
{ }
};
struct HttpOpenRequest : public OpenResource {
HttpOpenRequest(const Connect& h,
LPCTSTR verb, // TEXT("GET")
LPCTSTR objectName,
LPCTSTR version = NULL,
LPCTSTR referer = NULL,
LPCTSTR *acceptTypes = NULL,
DWORD flags = 0,
DWORD_PTR context = NULL
) : OpenResource(::HttpOpenRequest(h, verb, objectName, version, referer, acceptTypes, flags, context))
{ }
BOOL HttpAddRequestHeaders(
LPCTSTR headers,
DWORD headersLength = -1, // NULL terminated
DWORD modifiers = HTTP_ADDREQ_FLAG_ADD_IF_NEW
)
{
return ::HttpAddRequestHeaders(*this, headers, headersLength, modifiers);
}
BOOL HttpSendRequest(
LPCTSTR headers = TEXT(""),
DWORD headersLength = -1, // NULL terminated
LPVOID optional = NULL,
DWORD optionalLength = 0
)
{
return ::HttpSendRequest(*this, headers, headersLength, optional, optionalLength);
}
BOOL HttpQueryInfo(
DWORD infoLevel,
LPVOID buffer,
LPDWORD bufferLength,
LPDWORD index
)
{
return ::HttpQueryInfo(*this, infoLevel, buffer, bufferLength, index);
}
template<class BUFFER = std::basic_string<TCHAR>>
std::optional<BUFFER> HttpQueryInfo(DWORD infoLevel)
{
BUFFER buffer;
DWORD bufferLength = 0;
HttpQueryInfo(infoLevel, nullptr, &bufferLength, NULL);
DWORD error = GetLastError();
if (error == ERROR_HTTP_HEADER_NOT_FOUND) {
return {};
}
if (error == ERROR_INSUFFICIENT_BUFFER) {
buffer.resize(bufferLength);
}
if (HttpQueryInfo(infoLevel, buffer.data(), &bufferLength, NULL)) {
return buffer;
}
return {};
}
};
};
} // Win