유니티에서 http/https 통신하는 방법은 어셋을 사용하지 않는 선에서 크게 3가지 존재한다.
1. WWW
2. UnityWebRequest
3. HttpWebRequest
3가지 모두 HTTP 통신에는 문제가 없다.
하지만 HTTPS에서는 문제가 발생한다.
어떤 문제가 있었는지 정리해 본다.
인증서 만드는 법은 여기서
인증서 만들 때, CN값을 MERONG으로 입력해 뒀다.
Unity3d에서 https post로 통신하는 테스트 코드
IEnumerator TestHttpPost(string uri, byte[] bodyData)
{
////////////////////////////////////////////////////////////////////////////////////////////////////////////
// for WWW
////////////////////////////////////////////////////////////////////////////////////////////////////////////
WWW www = new WWW(uri, bodyData);
yield return www;
Debug.Log("www:" + www.error + " responsed data len:" + www.bytesDownloaded);
////////////////////////////////////////////////////////////////////////////////////////////////////////////
// for UnityWebRequest
////////////////////////////////////////////////////////////////////////////////////////////////////////////
UnityWebRequest unityWebRequest = UnityWebRequest.Post(uri, Encoding.ASCII.GetString(bodyData));
//UnityWebRequest unityWebRequest = UnityWebRequest.Put(uri, Encoding.ASCII.GetString(bodyData));
yield return unityWebRequest.Send();
if (unityWebRequest.isError)
{
Debug.Log("UnityWebRequest:" + unityWebRequest.error);
}
else
{
Debug.Log("UnityWebRequest: responsed data len:" + unityWebRequest.downloadedBytes);
}
////////////////////////////////////////////////////////////////////////////////////////////////////////////
// for HttpWebRequest
////////////////////////////////////////////////////////////////////////////////////////////////////////////
ServicePointManager.ServerCertificateValidationCallback = delegate
{
return true;
};
HttpWebRequest httpWebRequest = (HttpWebRequest)WebRequest.Create(uri);
httpWebRequest.Method = "POST";
httpWebRequest.ContentType = "application/octet-stream";
httpWebRequest.ContentLength = bodyData.Length;
httpWebRequest.BeginGetRequestStream(new AsyncCallback((iar) =>{
try
{
using (Stream stream = httpWebRequest.EndGetRequestStream(iar))
{
if (bodyData != null)
{
stream.Write(bodyData, 0, bodyData.Length);
}
stream.Close();
httpWebRequest.BeginGetResponse(new AsyncCallback((IAsyncResult iarres) =>{
try
{
using (HttpWebResponse response = (HttpWebResponse)httpWebRequest.EndGetResponse(iarres))
{
using (StreamReader streamReader = new StreamReader(response.GetResponseStream()))
{
Debug.Log("HttpWebRequest: responsed data len:" + streamReader.ReadToEnd().Length);
}
response.Close();
}
}
catch (Exception e)
{
Debug.Log(e);
}
}), null);
}
}
catch (Exception e)
{
Debug.Log(e);
}
}), null);
}
void Start() {
StartCoroutine(TestHttpPost("https://localhost:8443" + "/hellomvc2/", new byte[] { 61, 61 }));
}
WWW에서 오류발생
www:SSL: certificate subject name 'MERONG' does not match target host name 'localhost' responsed data len:0
UnityEngine.Debug:Log(Object)
c__Iterator0:MoveNext() (at Assets/Scripts/UIs/LoginGUI.cs:169)
UnityEngine.SetupCoroutine:InvokeMoveNext(IEnumerator, IntPtr)
UnityWebRequest 오류발생
UnityWebRequest:Unknown Error
UnityEngine.Debug:Log(Object)
c__Iterator0:MoveNext() (at Assets/Scripts/UIs/LoginGUI.cs:159)
UnityEngine.SetupCoroutine:InvokeMoveNext(IEnumerator, IntPtr)
HttpWebRequest에서 예외발생
System.Net.WebException: Error getting response stream (Write: The authentication or decryption has failed.): SendFailure ---> System.IO.IOException: The authentication or decryption has failed. ---> Mono.Security.Protocol.Tls.TlsException: The authentication or decryption has failed.
at Mono.Security.Protocol.Tls.RecordProtocol.ProcessAlert (AlertLevel alertLevel, AlertDescription alertDesc) [0x00000] in :0
at Mono.Security.Protocol.Tls.RecordProtocol.InternalReceiveRecordCallback (IAsyncResult asyncResult) [0x00000] in :0
--- End of inner exception stack trace ---
at Mono.Security.Protocol.Tls.SslStreamBase.AsyncHandshakeCallback (IAsyncResult asyncResult) [0x00000] in :0
--- End of inner exception stack trace ---
at System.Net.HttpWebRequest.EndGetRequestStream (IAsyncResult asyncResult) [0x00000] in :0
at LoginGUI+c__Iterator0+c__AnonStorey1.<>m__0 (IAsyncResult iar) [0x00009] in G:\project\BlueFin\bluefin_dev\server\unity3d_workspace\CS_Sample\Sample\Assets\Scripts\UIs\LoginGUI.cs:115
UnityEngine.Debug:Log(Object)
c__AnonStorey1:<>m__0(IAsyncResult) (at Assets/Scripts/UIs/LoginGUI.cs:148)
System.Net.WebConnection:InitConnection(Object)
WWW에서 발생한 오류
www:SSL: certificate subject name 'MERONG' does not match target host name 'localhost'
인증서 CN 값과 연결하려는 호스트 이름이 다르단다.
인증서 만들 때, localhost 를 입력하고 다시 실행해 보자.
www: responsed data len:134
UnityWebRequest: responsed data len:134
System.Net.WebException: Error getting response stream (Write: The authentication or decryption has failed.): SendFailure ---> System.IO.IOException: The authentication or decryption has failed. ---> Mono.Security.Protocol.Tls.TlsException: The authentication or decryption has failed.
at Mono.Security.Protocol.Tls.RecordProtocol.ProcessAlert (AlertLevel alertLevel, AlertDescription alertDesc) [0x00000] in :0
at Mono.Security.Protocol.Tls.RecordProtocol.InternalReceiveRecordCallback (IAsyncResult asyncResult) [0x00000] in :0
--- End of inner exception stack trace ---
at Mono.Security.Protocol.Tls.SslStreamBase.AsyncHandshakeCallback (IAsyncResult asyncResult) [0x00000] in :0
--- End of inner exception stack trace ---
at System.Net.HttpWebRequest.EndGetRequestStream (IAsyncResult asyncResult) [0x00000] in :0
at LoginGUI+c__Iterator0+c__AnonStorey1.<>m__0 (IAsyncResult iar) [0x00009] in G:\project\BlueFin\bluefin_dev\server\unity3d_workspace\CS_Sample\Sample\Assets\Scripts\UIs\LoginGUI.cs:142
UnityEngine.Debug:Log(Object)
c__AnonStorey1:<>m__0(IAsyncResult) (at Assets/Scripts/UIs/LoginGUI.cs:175)
System.Net.WebConnection:InitConnection(Object)
이번엔,
WWW과 UnityWebRequest는 정상이지만,
HttpWebRequest 여전히 같은 오류가 난다.
인증서 CN값이 달라서 오류가 발생한게 아니었다.
HTTPS 통신 성공 이후에 테스트 해 본거지만,
ServicePointManager.ServerCertificateValidationCallback 리턴값을 true로 해줬기 때문에.
인증서 CN값과 호스트 이름이 달라도 동작했다.
이 문제는,
SSL 핸드세이킹 중 복호화 실패 오류인데,
정말 이 문제로 고생 많이 했다. CA로 부터 인증을 못받아서 그런가 싶어
openssl로 CA 인증서도 만들어 봤지만 결과는 동일했다.
다행히,
openssl을 만지는 과정에서 https 사이트에 연결테스트를 해볼 수 있었는데, 거기서 차이점을 발견하게 되었다.
openssl로 localhost와 google를 연결해보았다.
$ openssl s_client -connect localhost:8443 -tls1
Loading 'screen' into random state - done
CONNECTED(00000188)
depth=0 /C=kr/ST=seoul/L=seoul/O=company/OU=team/CN=localhost
verify error:num=18:self signed certificate
verify return:1
depth=0 /C=kr/ST=seoul/L=seoul/O=company/OU=team/CN=localhost
verify return:1
---
Certificate chain
0 s:/C=kr/ST=seoul/L=seoul/O=company/OU=team/CN=localhost
i:/C=kr/ST=seoul/L=seoul/O=company/OU=team/CN=localhost
---
Server certificate
-----BEGIN CERTIFICATE-----
MIIDYzCCAkugAwIBAgIELIf7OjANBgkqhkiG9w0BAQsFADBiMQswCQYDVQQGEwJr
cjEOMAwGA1UECBMFc2VvdWwxDjAMBgNVBAcTBXNlb3VsMRAwDgYDVQQKEwdjb21w
YW55MQ0wCwYDVQQLEwR0ZWFtMRIwEAYDVQQDEwlsb2NhbGhvc3QwHhcNMTcwNDIx
MDYwMTQ5WhcNMjcwNDE5MDYwMTQ5WjBiMQswCQYDVQQGEwJrcjEOMAwGA1UECBMF
c2VvdWwxDjAMBgNVBAcTBXNlb3VsMRAwDgYDVQQKEwdjb21wYW55MQ0wCwYDVQQL
EwR0ZWFtMRIwEAYDVQQDEwlsb2NhbGhvc3QwggEiMA0GCSqGSIb3DQEBAQUAA4IB
DwAwggEKAoIBAQDigSpCI32KkfyIIff1bFe8vBkrxc+sVcCrlLLqach4tBcVn9Ef
3+IS4D0+ou78tijo+zFMlchtHMFTIcVZjwpLbvhR3VW1K1Hu6KGy+wEtB4jEleh1
4a0OkpQUKbiopAG5Hp7jQ77SSsr5M9NLTZuGRlDbylW9ZfkjgQ+nuGTbySrAUPmM
Q6d098q59n/nnvVuSci74RPZ1XEC/OLRsr5/yh5hmzNK3rI75A4r0QEiX9DK605P
TZtzGa/NOJiYIusuJuOzaJRfp8WewPJxAiWh4Y9Eh2+h+29SfXoN0yvhmrG+s8SZ
lpHK/7/cwHsi6ftCbsE+tUz5dtfXl3dsgqsXAgMBAAGjITAfMB0GA1UdDgQWBBQK
h8+3q7PMasozo3uTh3j44+TvozANBgkqhkiG9w0BAQsFAAOCAQEAhEIBdkkP7n1z
oS9O8JuaCkhFzurk8gh2aImhAPCyEMgPtG36+LKxsjrxicOmUniqbm6E817u/4l9
yVyslOzNOgC4K+acg//JcSfVOz6yVjJuoaeTDPQ9QtKZzNwex1On6OSIR83Aicru
PcAxkicupj7PHQ2mPlLeevCX00ZyInX5Xaqa7CIffeM8b+ZgCt+s/P7H/MZm198V
pAPcQgY9vkX+wv9UHNDPZEkjfE5wNWzEPbpo3EzCG4xfpJITGDEAbsQiEVfBQiAW
bnlEKoTnlImF+hOLj0esqvtqH45R9nwR/IXTJP4skz5ZwwxqDtA+klB4Exqf0qhO
DGmUUE37Vg==
-----END CERTIFICATE-----
subject=/C=kr/ST=seoul/L=seoul/O=company/OU=team/CN=localhost
issuer=/C=kr/ST=seoul/L=seoul/O=company/OU=team/CN=localhost
---
No client certificate CA names sent
---
SSL handshake has read 1548 bytes and written 292 bytes
---
New, TLSv1/SSLv3, Cipher is DHE-RSA-AES128-SHA
Server public key is 2048 bit
Compression: NONE
Expansion: NONE
SSL-Session:
Protocol : TLSv1
Cipher : DHE-RSA-AES128-SHA
Session-ID: 58F9A34D462F3565E4A1B8354E756B1A690EEE71D6F8364BD77100ADA13FCB71
Session-ID-ctx:
Master-Key: 4FEF0288D2D823960397C964A7D360C79F38AD840CFA27C312530EDD9097B89C
A51950A477E16CFE86E8429166DFBA72
Key-Arg : None
Start Time: 1492755277
Timeout : 7200 (sec)
Verify return code: 18 (self signed certificate)
---
$ openssl s_client -connect google.com:443 -tls1
Loading 'screen' into random state - done
CONNECTED(00000188)
depth=2 /C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
verify error:num=20:unable to get local issuer certificate
verify return:0
---
Certificate chain
0 s:/C=US/ST=California/L=Mountain View/O=Google Inc/CN=google.com
i:/C=US/O=Google Inc/CN=Google Internet Authority G2
1 s:/C=US/O=Google Inc/CN=Google Internet Authority G2
i:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
2 s:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
i:/C=US/O=Equifax/OU=Equifax Secure Certificate Authority
---
Server certificate
-----BEGIN CERTIFICATE-----
MIIgkjCCH3qgAwIBAgIIPUHY0Fje+9UwDQYJKoZIhvcNAQELBQAwSTELMAkGA1UE
BhMCVVMxEzARBgNVBAoTCkdvb2dsZSBJbmMxJTAjBgNVBAMTHEdvb2dsZSBJbnRl
cm5ldCBBdXRob3JpdHkgRzIwHhcNMTcwNDEyMTMzMDAxWhcNMTcwNzA1MTMyODAw
WjBkMQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQGA1UEBwwN
TW91bnRhaW4gVmlldzETMBEGA1UECgwKR29vZ2xlIEluYzETMBEGA1UEAwwKZ29v
Z2xlLmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALef9Jnvrg0F
9KgR3b6/OP8C9k8kXK75uyiNi+E1p/rnfLetVdab8iryadM7Rzbn5tHPUEQDZW/I
PBWC97vmA/DFKOBXkBvZJUppXHtchBellktHW/BtSqvMQW6QWAnHNsbcBWioUrd+
9gI9MNPwQDECLU/dA4qfszn0XOd/ctyNKavbJH4HOm+arET/kmVA67SLccmDoSFf
5aIIJe8Kl5F1KZtn4AWEgcW8j00RKQpdNKrNwYOMrEYJ+C86RHFwNsocK+aRKGNv
FbpifWXeBN170xxN9rjjXBobCKy6Z56+qZEwQTXIhW7s0yXpI6AXfZfZAqdJGs29
nADFSLgJttkCAwEAAaOCHWEwgh1dMB0GA1UdJQQWMBQGCCsGAQUFBwMBBggrBgEF
BQcDAjCCHC0GA1UdEQSCHCQwghwgggpnb29nbGUuY29tggoqLjJtZG4ubmV0gg0q
LmFuZHJvaWQuY29tghYqLmFwcGVuZ2luZS5nb29nbGUuY29tghQqLmF1LmRvdWJs
ZWNsaWNrLm5ldIILKi5jYy1kdC5jb22CEiouY2xvdWQuZ29vZ2xlLmNvbYIUKi5k
ZS5kb3VibGVjbGljay5uZXSCESouZG91YmxlY2xpY2suY29tghEqLmRvdWJsZWNs
aWNrLm5ldIIVKi5mbHMuZG91YmxlY2xpY2submV0ghQqLmZyLmRvdWJsZWNsaWNr
Lm5ldIIOKi5nY3AuZ3Z0Mi5jb22CFiouZ29vZ2xlLWFuYWx5dGljcy5jb22CCyou
Z29vZ2xlLmFjggsqLmdvb2dsZS5hZIILKi5nb29nbGUuYWWCCyouZ29vZ2xlLmFm
ggsqLmdvb2dsZS5hZ4ILKi5nb29nbGUuYWyCCyouZ29vZ2xlLmFtggsqLmdvb2ds
ZS5hc4ILKi5nb29nbGUuYXSCCyouZ29vZ2xlLmF6ggsqLmdvb2dsZS5iYYILKi5n
b29nbGUuYmWCCyouZ29vZ2xlLmJmggsqLmdvb2dsZS5iZ4ILKi5nb29nbGUuYmmC
CyouZ29vZ2xlLmJqggsqLmdvb2dsZS5ic4ILKi5nb29nbGUuYnSCCyouZ29vZ2xl
LmJ5ggsqLmdvb2dsZS5jYYIMKi5nb29nbGUuY2F0ggsqLmdvb2dsZS5jY4ILKi5n
b29nbGUuY2SCCyouZ29vZ2xlLmNmggsqLmdvb2dsZS5jZ4ILKi5nb29nbGUuY2iC
CyouZ29vZ2xlLmNpggsqLmdvb2dsZS5jbIILKi5nb29nbGUuY22CCyouZ29vZ2xl
LmNugg4qLmdvb2dsZS5jby5hb4IOKi5nb29nbGUuY28uYneCDiouZ29vZ2xlLmNv
LmNrgg4qLmdvb2dsZS5jby5jcoIOKi5nb29nbGUuY28uaHWCDiouZ29vZ2xlLmNv
Lmlkgg4qLmdvb2dsZS5jby5pbIIOKi5nb29nbGUuY28uaW2CDiouZ29vZ2xlLmNv
Lmlugg4qLmdvb2dsZS5jby5qZYIOKi5nb29nbGUuY28uanCCDiouZ29vZ2xlLmNv
Lmtlgg4qLmdvb2dsZS5jby5rcoIOKi5nb29nbGUuY28ubHOCDiouZ29vZ2xlLmNv
Lm1hgg4qLmdvb2dsZS5jby5teoIOKi5nb29nbGUuY28ubnqCDiouZ29vZ2xlLmNv
LnRogg4qLmdvb2dsZS5jby50eoIOKi5nb29nbGUuY28udWeCDiouZ29vZ2xlLmNv
LnVrgg4qLmdvb2dsZS5jby51eoIOKi5nb29nbGUuY28udmWCDiouZ29vZ2xlLmNv
LnZpgg4qLmdvb2dsZS5jby56YYIOKi5nb29nbGUuY28uem2CDiouZ29vZ2xlLmNv
Lnp3ggwqLmdvb2dsZS5jb22CDyouZ29vZ2xlLmNvbS5hZoIPKi5nb29nbGUuY29t
LmFngg8qLmdvb2dsZS5jb20uYWmCDyouZ29vZ2xlLmNvbS5hcoIPKi5nb29nbGUu
Y29tLmF1gg8qLmdvb2dsZS5jb20uYmSCDyouZ29vZ2xlLmNvbS5iaIIPKi5nb29n
bGUuY29tLmJugg8qLmdvb2dsZS5jb20uYm+CDyouZ29vZ2xlLmNvbS5icoIPKi5n
b29nbGUuY29tLmJ5gg8qLmdvb2dsZS5jb20uYnqCDyouZ29vZ2xlLmNvbS5jboIP
Ki5nb29nbGUuY29tLmNvgg8qLmdvb2dsZS5jb20uY3WCDyouZ29vZ2xlLmNvbS5j
eYIPKi5nb29nbGUuY29tLmRvgg8qLmdvb2dsZS5jb20uZWOCDyouZ29vZ2xlLmNv
bS5lZ4IPKi5nb29nbGUuY29tLmV0gg8qLmdvb2dsZS5jb20uZmqCDyouZ29vZ2xl
LmNvbS5nZYIPKi5nb29nbGUuY29tLmdogg8qLmdvb2dsZS5jb20uZ2mCDyouZ29v
Z2xlLmNvbS5ncoIPKi5nb29nbGUuY29tLmd0gg8qLmdvb2dsZS5jb20uaGuCDyou
Z29vZ2xlLmNvbS5pcYIPKi5nb29nbGUuY29tLmptgg8qLmdvb2dsZS5jb20uam+C
DyouZ29vZ2xlLmNvbS5raIIPKi5nb29nbGUuY29tLmt3gg8qLmdvb2dsZS5jb20u
bGKCDyouZ29vZ2xlLmNvbS5seYIPKi5nb29nbGUuY29tLm1tgg8qLmdvb2dsZS5j
b20ubXSCDyouZ29vZ2xlLmNvbS5teIIPKi5nb29nbGUuY29tLm15gg8qLmdvb2ds
ZS5jb20ubmGCDyouZ29vZ2xlLmNvbS5uZoIPKi5nb29nbGUuY29tLm5ngg8qLmdv
b2dsZS5jb20ubmmCDyouZ29vZ2xlLmNvbS5ucIIPKi5nb29nbGUuY29tLm5ygg8q
Lmdvb2dsZS5jb20ub22CDyouZ29vZ2xlLmNvbS5wYYIPKi5nb29nbGUuY29tLnBl
gg8qLmdvb2dsZS5jb20ucGeCDyouZ29vZ2xlLmNvbS5waIIPKi5nb29nbGUuY29t
LnBrgg8qLmdvb2dsZS5jb20ucGyCDyouZ29vZ2xlLmNvbS5wcoIPKi5nb29nbGUu
Y29tLnB5gg8qLmdvb2dsZS5jb20ucWGCDyouZ29vZ2xlLmNvbS5ydYIPKi5nb29n
bGUuY29tLnNhgg8qLmdvb2dsZS5jb20uc2KCDyouZ29vZ2xlLmNvbS5zZ4IPKi5n
b29nbGUuY29tLnNsgg8qLmdvb2dsZS5jb20uc3aCDyouZ29vZ2xlLmNvbS50aoIP
Ki5nb29nbGUuY29tLnRugg8qLmdvb2dsZS5jb20udHKCDyouZ29vZ2xlLmNvbS50
d4IPKi5nb29nbGUuY29tLnVhgg8qLmdvb2dsZS5jb20udXmCDyouZ29vZ2xlLmNv
bS52Y4IPKi5nb29nbGUuY29tLnZlgg8qLmdvb2dsZS5jb20udm6CCyouZ29vZ2xl
LmN2ggsqLmdvb2dsZS5jeoILKi5nb29nbGUuZGWCCyouZ29vZ2xlLmRqggsqLmdv
b2dsZS5ka4ILKi5nb29nbGUuZG2CCyouZ29vZ2xlLmR6ggsqLmdvb2dsZS5lZYIL
Ki5nb29nbGUuZXOCDCouZ29vZ2xlLmV1c4ILKi5nb29nbGUuZmmCCyouZ29vZ2xl
LmZtggsqLmdvb2dsZS5mcoIMKi5nb29nbGUuZnJsggsqLmdvb2dsZS5nYYIMKi5n
b29nbGUuZ2FsggsqLmdvb2dsZS5nZYILKi5nb29nbGUuZ2eCCyouZ29vZ2xlLmds
ggsqLmdvb2dsZS5nbYILKi5nb29nbGUuZ3CCCyouZ29vZ2xlLmdyggsqLmdvb2ds
ZS5neYILKi5nb29nbGUuaGuCCyouZ29vZ2xlLmhuggsqLmdvb2dsZS5ocoILKi5n
b29nbGUuaHSCCyouZ29vZ2xlLmh1ggsqLmdvb2dsZS5pZYILKi5nb29nbGUuaW2C
CyouZ29vZ2xlLmlugg0qLmdvb2dsZS5pbmZvggsqLmdvb2dsZS5pcYILKi5nb29n
bGUuaXKCCyouZ29vZ2xlLmlzggsqLmdvb2dsZS5pdIIOKi5nb29nbGUuaXQuYW+C
CyouZ29vZ2xlLmplggsqLmdvb2dsZS5qb4INKi5nb29nbGUuam9ic4ILKi5nb29n
bGUuanCCCyouZ29vZ2xlLmtnggsqLmdvb2dsZS5raYILKi5nb29nbGUua3qCCyou
Z29vZ2xlLmxhggsqLmdvb2dsZS5saYILKi5nb29nbGUubGuCCyouZ29vZ2xlLmx0
ggsqLmdvb2dsZS5sdYILKi5nb29nbGUubHaCCyouZ29vZ2xlLm1kggsqLmdvb2ds
ZS5tZYILKi5nb29nbGUubWeCCyouZ29vZ2xlLm1rggsqLmdvb2dsZS5tbIILKi5n
b29nbGUubW6CCyouZ29vZ2xlLm1zggsqLmdvb2dsZS5tdYILKi5nb29nbGUubXaC
CyouZ29vZ2xlLm13ggsqLmdvb2dsZS5uZYIOKi5nb29nbGUubmUuanCCDCouZ29v
Z2xlLm5ldIILKi5nb29nbGUubmeCCyouZ29vZ2xlLm5sggsqLmdvb2dsZS5ub4IL
Ki5nb29nbGUubnKCCyouZ29vZ2xlLm51gg8qLmdvb2dsZS5vZmYuYWmCCyouZ29v
Z2xlLnBrggsqLmdvb2dsZS5wbIILKi5nb29nbGUucG6CCyouZ29vZ2xlLnBzggsq
Lmdvb2dsZS5wdIILKi5nb29nbGUucm+CCyouZ29vZ2xlLnJzggsqLmdvb2dsZS5y
dYILKi5nb29nbGUucneCCyouZ29vZ2xlLnNjggsqLmdvb2dsZS5zZYILKi5nb29n
bGUuc2iCCyouZ29vZ2xlLnNpggsqLmdvb2dsZS5za4ILKi5nb29nbGUuc22CCyou
Z29vZ2xlLnNuggsqLmdvb2dsZS5zb4ILKi5nb29nbGUuc3KCCyouZ29vZ2xlLnN0
ggsqLmdvb2dsZS50ZIIMKi5nb29nbGUudGVsggsqLmdvb2dsZS50Z4ILKi5nb29n
bGUudGuCCyouZ29vZ2xlLnRsggsqLmdvb2dsZS50bYILKi5nb29nbGUudG6CCyou
Z29vZ2xlLnRvggsqLmdvb2dsZS50dIILKi5nb29nbGUudWGCCyouZ29vZ2xlLnVz
ggsqLmdvb2dsZS51eoILKi5nb29nbGUudmeCCyouZ29vZ2xlLnZ1ggsqLmdvb2ds
ZS53c4ISKi5nb29nbGVhZGFwaXMuY29tghUqLmdvb2dsZWFkc3NlcnZpbmcuY26C
DyouZ29vZ2xlYXBpcy5jboIUKi5nb29nbGVjb21tZXJjZS5jb22CFiouZ29vZ2xl
dXNlcmNvbnRlbnQuY26CESouZ29vZ2xldmlkZW8uY29tggwqLmdzdGF0aWMuY26C
DSouZ3N0YXRpYy5jb22CCiouZ3Z0MS5jb22CCiouZ3Z0Mi5jb22CFCouanAuZG91
YmxlY2xpY2submV0ghQqLm1ldHJpYy5nc3RhdGljLmNvbYIUKi51ay5kb3VibGVj
bGljay5uZXSCDCoudXJjaGluLmNvbYIQKi51cmwuZ29vZ2xlLmNvbYIWKi55b3V0
dWJlLW5vY29va2llLmNvbYINKi55b3V0dWJlLmNvbYIWKi55b3V0dWJlZWR1Y2F0
aW9uLmNvbYILKi55dGltZy5jb22CFWFkLm1vLmRvdWJsZWNsaWNrLm5ldIIaYW5k
cm9pZC5jbGllbnRzLmdvb2dsZS5jb22CC2FuZHJvaWQuY29tghtkZXZlbG9wZXIu
YW5kcm9pZC5nb29nbGUuY26CHGRldmVsb3BlcnMuYW5kcm9pZC5nb29nbGUuY26C
D2RvdWJsZWNsaWNrLmNvbYIPZG91YmxlY2xpY2submV0ggRnLmNvggZnb28uZ2yC
FGdvb2dsZS1hbmFseXRpY3MuY29tgglnb29nbGUuYWOCCWdvb2dsZS5hZIIJZ29v
Z2xlLmFlgglnb29nbGUuYWaCCWdvb2dsZS5hZ4IJZ29vZ2xlLmFsgglnb29nbGUu
YW2CCWdvb2dsZS5hc4IJZ29vZ2xlLmF0gglnb29nbGUuYXqCCWdvb2dsZS5iYYIJ
Z29vZ2xlLmJlgglnb29nbGUuYmaCCWdvb2dsZS5iZ4IJZ29vZ2xlLmJpgglnb29n
bGUuYmqCCWdvb2dsZS5ic4IJZ29vZ2xlLmJ0gglnb29nbGUuYnmCCWdvb2dsZS5j
YYIKZ29vZ2xlLmNhdIIJZ29vZ2xlLmNjgglnb29nbGUuY2SCCWdvb2dsZS5jZoIJ
Z29vZ2xlLmNngglnb29nbGUuY2iCCWdvb2dsZS5jaYIJZ29vZ2xlLmNsgglnb29n
bGUuY22CCWdvb2dsZS5jboIMZ29vZ2xlLmNvLmFvggxnb29nbGUuY28uYneCDGdv
b2dsZS5jby5ja4IMZ29vZ2xlLmNvLmNyggxnb29nbGUuY28uaHWCDGdvb2dsZS5j
by5pZIIMZ29vZ2xlLmNvLmlsggxnb29nbGUuY28uaW2CDGdvb2dsZS5jby5pboIM
Z29vZ2xlLmNvLmplggxnb29nbGUuY28uanCCDGdvb2dsZS5jby5rZYIMZ29vZ2xl
LmNvLmtyggxnb29nbGUuY28ubHOCDGdvb2dsZS5jby5tYYIMZ29vZ2xlLmNvLm16
ggxnb29nbGUuY28ubnqCDGdvb2dsZS5jby50aIIMZ29vZ2xlLmNvLnR6ggxnb29n
bGUuY28udWeCDGdvb2dsZS5jby51a4IMZ29vZ2xlLmNvLnV6ggxnb29nbGUuY28u
dmWCDGdvb2dsZS5jby52aYIMZ29vZ2xlLmNvLnphggxnb29nbGUuY28uem2CDGdv
b2dsZS5jby56d4INZ29vZ2xlLmNvbS5hZoINZ29vZ2xlLmNvbS5hZ4INZ29vZ2xl
LmNvbS5haYINZ29vZ2xlLmNvbS5hcoINZ29vZ2xlLmNvbS5hdYINZ29vZ2xlLmNv
bS5iZIINZ29vZ2xlLmNvbS5iaIINZ29vZ2xlLmNvbS5iboINZ29vZ2xlLmNvbS5i
b4INZ29vZ2xlLmNvbS5icoINZ29vZ2xlLmNvbS5ieYINZ29vZ2xlLmNvbS5ieoIN
Z29vZ2xlLmNvbS5jboINZ29vZ2xlLmNvbS5jb4INZ29vZ2xlLmNvbS5jdYINZ29v
Z2xlLmNvbS5jeYINZ29vZ2xlLmNvbS5kb4INZ29vZ2xlLmNvbS5lY4INZ29vZ2xl
LmNvbS5lZ4INZ29vZ2xlLmNvbS5ldIINZ29vZ2xlLmNvbS5maoINZ29vZ2xlLmNv
bS5nZYINZ29vZ2xlLmNvbS5naIINZ29vZ2xlLmNvbS5naYINZ29vZ2xlLmNvbS5n
coINZ29vZ2xlLmNvbS5ndIINZ29vZ2xlLmNvbS5oa4INZ29vZ2xlLmNvbS5pcYIN
Z29vZ2xlLmNvbS5qbYINZ29vZ2xlLmNvbS5qb4INZ29vZ2xlLmNvbS5raIINZ29v
Z2xlLmNvbS5rd4INZ29vZ2xlLmNvbS5sYoINZ29vZ2xlLmNvbS5seYINZ29vZ2xl
LmNvbS5tbYINZ29vZ2xlLmNvbS5tdIINZ29vZ2xlLmNvbS5teIINZ29vZ2xlLmNv
bS5teYINZ29vZ2xlLmNvbS5uYYINZ29vZ2xlLmNvbS5uZoINZ29vZ2xlLmNvbS5u
Z4INZ29vZ2xlLmNvbS5uaYINZ29vZ2xlLmNvbS5ucIINZ29vZ2xlLmNvbS5ucoIN
Z29vZ2xlLmNvbS5vbYINZ29vZ2xlLmNvbS5wYYINZ29vZ2xlLmNvbS5wZYINZ29v
Z2xlLmNvbS5wZ4INZ29vZ2xlLmNvbS5waIINZ29vZ2xlLmNvbS5wa4INZ29vZ2xl
LmNvbS5wbIINZ29vZ2xlLmNvbS5wcoINZ29vZ2xlLmNvbS5weYINZ29vZ2xlLmNv
bS5xYYINZ29vZ2xlLmNvbS5ydYINZ29vZ2xlLmNvbS5zYYINZ29vZ2xlLmNvbS5z
YoINZ29vZ2xlLmNvbS5zZ4INZ29vZ2xlLmNvbS5zbIINZ29vZ2xlLmNvbS5zdoIN
Z29vZ2xlLmNvbS50aoINZ29vZ2xlLmNvbS50boINZ29vZ2xlLmNvbS50coINZ29v
Z2xlLmNvbS50d4INZ29vZ2xlLmNvbS51YYINZ29vZ2xlLmNvbS51eYINZ29vZ2xl
LmNvbS52Y4INZ29vZ2xlLmNvbS52ZYINZ29vZ2xlLmNvbS52boIJZ29vZ2xlLmN2
gglnb29nbGUuY3qCCWdvb2dsZS5kZYIJZ29vZ2xlLmRqgglnb29nbGUuZGuCCWdv
b2dsZS5kbYIJZ29vZ2xlLmR6gglnb29nbGUuZWWCCWdvb2dsZS5lc4IKZ29vZ2xl
LmV1c4IJZ29vZ2xlLmZpgglnb29nbGUuZm2CCWdvb2dsZS5mcoIKZ29vZ2xlLmZy
bIIJZ29vZ2xlLmdhggpnb29nbGUuZ2Fsgglnb29nbGUuZ2WCCWdvb2dsZS5nZ4IJ
Z29vZ2xlLmdsgglnb29nbGUuZ22CCWdvb2dsZS5ncIIJZ29vZ2xlLmdygglnb29n
bGUuZ3mCCWdvb2dsZS5oa4IJZ29vZ2xlLmhugglnb29nbGUuaHKCCWdvb2dsZS5o
dIIJZ29vZ2xlLmh1gglnb29nbGUuaWWCCWdvb2dsZS5pbYIJZ29vZ2xlLmluggtn
b29nbGUuaW5mb4IJZ29vZ2xlLmlxgglnb29nbGUuaXKCCWdvb2dsZS5pc4IJZ29v
Z2xlLml0ggxnb29nbGUuaXQuYW+CCWdvb2dsZS5qZYIJZ29vZ2xlLmpvggtnb29n
bGUuam9ic4IJZ29vZ2xlLmpwgglnb29nbGUua2eCCWdvb2dsZS5raYIJZ29vZ2xl
Lmt6gglnb29nbGUubGGCCWdvb2dsZS5saYIJZ29vZ2xlLmxrgglnb29nbGUubHSC
CWdvb2dsZS5sdYIJZ29vZ2xlLmx2gglnb29nbGUubWSCCWdvb2dsZS5tZYIJZ29v
Z2xlLm1ngglnb29nbGUubWuCCWdvb2dsZS5tbIIJZ29vZ2xlLm1ugglnb29nbGUu
bXOCCWdvb2dsZS5tdYIJZ29vZ2xlLm12gglnb29nbGUubXeCCWdvb2dsZS5uZYIM
Z29vZ2xlLm5lLmpwggpnb29nbGUubmV0gglnb29nbGUubmeCCWdvb2dsZS5ubIIJ
Z29vZ2xlLm5vgglnb29nbGUubnKCCWdvb2dsZS5udYINZ29vZ2xlLm9mZi5haYIJ
Z29vZ2xlLnBrgglnb29nbGUucGyCCWdvb2dsZS5wboIJZ29vZ2xlLnBzgglnb29n
bGUucHSCCWdvb2dsZS5yb4IJZ29vZ2xlLnJzgglnb29nbGUucnWCCWdvb2dsZS5y
d4IJZ29vZ2xlLnNjgglnb29nbGUuc2WCCWdvb2dsZS5zaIIJZ29vZ2xlLnNpggln
b29nbGUuc2uCCWdvb2dsZS5zbYIJZ29vZ2xlLnNugglnb29nbGUuc2+CCWdvb2ds
ZS5zcoIJZ29vZ2xlLnN0gglnb29nbGUudGSCCmdvb2dsZS50ZWyCCWdvb2dsZS50
Z4IJZ29vZ2xlLnRrgglnb29nbGUudGyCCWdvb2dsZS50bYIJZ29vZ2xlLnRuggln
b29nbGUudG+CCWdvb2dsZS50dIIJZ29vZ2xlLnVhgglnb29nbGUudXOCCWdvb2ds
ZS51eoIJZ29vZ2xlLnZngglnb29nbGUudnWCCWdvb2dsZS53c4ISZ29vZ2xlY29t
bWVyY2UuY29tggtnc3RhdGljLmNvbYIYc291cmNlLmFuZHJvaWQuZ29vZ2xlLmNu
ggp1cmNoaW4uY29tggp3d3cuZ29vLmdsggh5b3V0dS5iZYILeW91dHViZS5jb22C
FHlvdXR1YmVlZHVjYXRpb24uY29tMGgGCCsGAQUFBwEBBFwwWjArBggrBgEFBQcw
AoYfaHR0cDovL3BraS5nb29nbGUuY29tL0dJQUcyLmNydDArBggrBgEFBQcwAYYf
aHR0cDovL2NsaWVudHMxLmdvb2dsZS5jb20vb2NzcDAdBgNVHQ4EFgQUPQcNoAjb
AaFeLXaduMux3LauOlEwDAYDVR0TAQH/BAIwADAfBgNVHSMEGDAWgBRK3QYWG7z2
aLV29YG2u2IaulqBLzAhBgNVHSAEGjAYMAwGCisGAQQB1nkCBQEwCAYGZ4EMAQIC
MDAGA1UdHwQpMCcwJaAjoCGGH2h0dHA6Ly9wa2kuZ29vZ2xlLmNvbS9HSUFHMi5j
cmwwDQYJKoZIhvcNAQELBQADggEBAJf7X+zcJzFGTH5aKJuP7D1DkBa757RB8Gkh
B+Y6q1OUWoKlO9GsdSYmZw01t3LB+OjI+B4fKn3S4XwDjiEHB5fw3g9btZD+Nu0H
mMIW3/1pPnc05aWoB9J3fc0yrX+Sczj5HaroYJgyjrr5AaPdaJmR0JLzdw9et4kZ
OELuRZpYOQulkciGogOlwbP/gC3MzEoKXJfQaJ6OK8D92PvnqTzAzCxLPuaOinFa
WgSO+Vk0tRzKcFYRJB2VQng8gmFzkQH9tVXLw4lqjSf8nHXLry4sNaZgUGiGSxKE
JhLO72lIz8k90hHn4KPHQF4fWCVIiVU6dGZeQSfGuhISjaWaou8=
-----END CERTIFICATE-----
subject=/C=US/ST=California/L=Mountain View/O=Google Inc/CN=google.com
issuer=/C=US/O=Google Inc/CN=Google Internet Authority G2
---
No client certificate CA names sent
---
SSL handshake has read 10572 bytes and written 420 bytes
---
New, TLSv1/SSLv3, Cipher is AES128-SHA
Server public key is 2048 bit
Compression: NONE
Expansion: NONE
SSL-Session:
Protocol : TLSv1
Cipher : AES128-SHA
Session-ID:
Session-ID-ctx:
Master-Key: BA2CBFF9CC73E8D62838CBB95F681DB9CFDBD58443668486245DEDB571C8B6EC
3B72E90BB7A35B6E78B6B09E31A27F8B
Key-Arg : None
TLS session ticket lifetime hint: 100800 (seconds)
TLS session ticket:
0000 - 52 ec 05 c8 ac 58 4c be-9f e7 df b7 5f db 2e 87 R....XL....._...
0010 - 8b c3 f2 18 31 43 e6 4c-63 de 0a 5d fa 0d 71 6b ....1C.Lc..]..qk
0020 - 56 8e c2 fe 98 db 25 b2-f1 66 a6 fa 39 86 1c b0 V.....%..f..9...
0030 - 04 de bb ba 82 20 f8 02-73 c8 a9 05 b0 ba 3b 85 ..... ..s.....;.
0040 - 12 dd ad bb 7d 1a 8d 5b-c3 35 0f 93 6e 8b 96 e2 ....}..[.5..n...
0050 - 0a 52 ab c1 f0 3d 77 3a-1b bd 45 cf 4a 7e 00 68 .R...=w:..E.J~.h
0060 - 6f 06 e4 9e a1 e4 1c a3-79 e7 87 5c 3c c4 11 f7 o.......y..\<...
0070 - 2f d8 95 cf 1b 79 1a 8a-b1 2d 27 5a 6e 3a 5d 90 /....y...-'Zn:].
0080 - 6b 5e a8 37 a9 61 06 df-54 4d 35 f0 2c d7 bd ae k^.7.a..TM5.,...
0090 - 53 19 54 00 05 0b 94 ab-b3 86 e3 21 6d dd 87 5c S.T........!m..\
00a0 - 79 a4 bb 75 y..u
Start Time: 1492755701
Timeout : 7200 (sec)
Verify return code: 20 (unable to get local issuer certificate)
---
SSL Cipher값이
localhost는 DHE-RSA-AES128-SHA이지만,
google은 AES128-SHA이다.
Tomcat server.xml에서 AES128-SHA 지원하도록 설정해보자.
Tomcat ciphers 값은 추천 암호화 목록이 있으니 참고해 보기
다시 테스트 코드 실행해 보기
www: responsed data len:134
UnityWebRequest: responsed data len:134
HttpWebRequest: responsed data len:134
모두 잘 받았다.
핸드쉐이킹 과정에서, 클라와 서버 모두 사용 가능한 암호기법이 있어야 했다.
유니티 모노버전이 낮아서 지원하는 암호기법이 한정적이었다.
뭐 어쨋든 성공!!
이번에는 서버에서 잘 받았는지 확인해 보자.
SpringFramework 기본 MVC이며,
POST, PUT 두 가지로 BODY데이터를 받도록 했고, 받은 BODY길이를 로그로 찍었다.
@RequestMapping(value = "/", method = RequestMethod.POST)
public String home(HttpServletRequest request, HttpServletResponse response, @RequestBody byte[] body) throws IOException {
logger.info("post:" + body.length);
return "home";
}
@RequestMapping(value = "/", method = RequestMethod.PUT)
public String homePut(HttpServletRequest request, HttpServletResponse response, @RequestBody byte[] body) throws IOException {
logger.info("put:" + body.length);
return "home";
}
서버 로그
INFO : bluefin.net.hellomvc2.HomeController - post:7
INFO : bluefin.net.hellomvc2.HomeController - post:7
INFO : bluefin.net.hellomvc2.HomeController - post:2
어라? 클라에서는 분명 new byte[]{61, 61}로 만들어 2바이트만 Body로 보냈다.
디버깅 결과 post:7을 남긴 녀석들은 WWW과 UnityWebRequest였다.

서버가 받은 데이터를 아스키문자로 변환하면 "%3E%3E="이다.
URLENCODE도 아니고 BASE64도 아니고 뭔지 모르겠다^^
스트링을 컨버전하는 사이트에서 확인해 봤는데, URLENCODE로 하는게 가장 비슷하게 나왔다.
문제는 WWW와 UnityWebRequest는 POST로 문자열만 보낼 수 있다.
바이너리 데이터를 보내고 싶었다.
UnityWebRequest에는 다행히 PUT으로 바이너리로 보낼 수 있었다.
테스트 결과는 put:2를 잘 남겼다.
http body에 바이너리를 담으려면, UnityWebRequest.PUT 또는 HttpWebRequest를 사용해야 한다.
간만에 긴 글을 작성했다.
시작은 HTTPS 통신이었고, 통신이 되면서 바이너리 통신을 해봤다, 결과는 휴 힘들었다^^
도움 되시길~