sync with tizen_2.0
[platform/framework/native/appfw.git] / src / base / utility / FBaseUtilUrlEncoder.cpp
1 //
2 // Open Service Platform
3 // Copyright (c) 2012 Samsung Electronics Co., Ltd.
4 //
5 // Licensed under the Apache License, Version 2.0 (the License);
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 // http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17
18 /**
19  * @file                FBaseUtilUrlEncoder.cpp
20  * @brief               This is the implementation file for UrlEncoder class.
21  */
22
23 // Includes
24 #include <stdio.h>
25 #include <stdlib.h>
26 #include <wchar.h>
27 #include <string.h>
28 #include <new>
29 #include <unique_ptr.h>
30 #include <unicode/ustring.h>
31 #include <unicode/utypes.h>
32 #include <unicode/ucnv.h>
33 #include <FBaseUtilUrlEncoder.h>
34 #include <FBaseResult.h>
35 #include <FBaseSysLog.h>
36 #include "FBase_StringConverter.h"
37 #include "FBase_NativeError.h"
38 #include "FBaseUtil_IcuConverter.h"
39
40
41 namespace Tizen { namespace Base { namespace Utility
42 {
43
44
45 ///////////////////////////////////////////////////////////////////////////////
46 /// UrlEncoder class lifecycle
47
48 UrlEncoder::UrlEncoder(void)
49 {
50 }
51
52
53 UrlEncoder::~UrlEncoder(void)
54 {
55 }
56
57
58 ///////////////////////////////////////////////////////////////////////////////
59 /// UrlEncoder class Operations
60
61 result
62 UrlEncoder::Encode(const Tizen::Base::String& str, const Tizen::Base::String& encodingScheme, Tizen::Base::String& encodedStr)
63 {
64         SysTryReturnResult(NID_BASE_UTIL, str.GetLength() > 0, E_INVALID_ARG, "Invalid argument is used. String to be encoded is empty.");
65         SysTryReturnResult(NID_BASE_UTIL, encodingScheme.GetLength() > 0, E_INVALID_ARG, "Invalid argument is used. Invalid encoding scheme.");
66
67         _ICUConverter converter;
68         bool converted = converter.OpenConverter(encodingScheme);
69         result r = GetLastResult();
70         SysTryReturnResult(NID_BASE_UTIL, converted, r, "Propagating.");
71
72         int startIndex = -1;
73         std::unique_ptr< char[] > pOutBuf(null);
74         const wchar_t* pTmpBytePtr = str.GetPointer();
75         encodedStr.Clear();
76         int strLen = str.GetLength();
77
78         for (int i = 0; i < strLen; i++)
79         {
80                 // Do not convert unreserved characters (Unreserved Characters for URI in RFC 3986)
81                 if ((pTmpBytePtr[i] >= 'a' && pTmpBytePtr[i] <= 'z') || (pTmpBytePtr[i] >= 'A' && pTmpBytePtr[i] <= 'Z') || (pTmpBytePtr[i] >= '0' && pTmpBytePtr[i] <= '9') || (pTmpBytePtr[i] == '_') || (pTmpBytePtr[i] == '~') || (pTmpBytePtr[i] == '-') || (pTmpBytePtr[i] == '.') || (pTmpBytePtr[i] == ' '))
82                 {
83                         if (startIndex >= 0)
84                         {
85                                 int retLength = 0;
86                                 pOutBuf.reset(converter.ConvertFromUcharN(pTmpBytePtr + startIndex, (i - startIndex), retLength));
87                                 r = GetLastResult();
88                                 SysTryReturnResult(NID_BASE_UTIL, pOutBuf != null, r, "Propagating.");
89
90                                 for (int j = 0; j < retLength; j++)
91                                 {
92
93                                         char hexChar[4];
94                                         memset(&hexChar, 0x00, 4);
95                                         sprintf(hexChar, "%%%02X", (unsigned char) pOutBuf[j]);
96                                         hexChar[3] = 0;
97                                         encodedStr.Append(hexChar); // Append %ab  buffer to encoded string
98                                 }
99                                 startIndex = -1;
100                         }
101
102                         (pTmpBytePtr[i] == ' ') ? encodedStr.Append('+'):encodedStr.Append(pTmpBytePtr[i]);
103                 }
104                 else if (startIndex < 0)
105                 {
106                         startIndex = i;
107                 }
108         }
109
110         if (startIndex >= 0)
111         {
112                 int retLength = 0;
113                 pOutBuf.reset(converter.ConvertFromUcharN(pTmpBytePtr + startIndex, (str.GetLength() - startIndex), retLength));
114                 r = GetLastResult();
115                 SysTryReturnResult(NID_BASE_UTIL, pOutBuf != null, r, GetErrorMessage(r));
116
117                 for (int j = 0; j < retLength; j++)
118                 {
119
120                         char hexChar[4];
121                         memset(&hexChar, 0x00, 4);
122                         sprintf(hexChar, "%%%02X", (unsigned char) pOutBuf[j]);
123                         hexChar[3] = 0;
124                         encodedStr.Append(hexChar); // Append %ab  buffer to encoded string
125                 }
126                 startIndex = -1;
127         }
128
129         converter.CloseConverter();
130         return r;
131 }
132 } } } // Tizen::Base::Utility