Advertisement
Guest User

Untitled

a guest
Jun 22nd, 2017
60
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
D 5.96 KB | None | 0 0
  1. import std.encoding;
  2. import std.stdio;
  3. import std.string;
  4. import std.conv;
  5. import std.algorithm;
  6. import std.stream;
  7.  
  8. /*
  9. Specs:
  10.  
  11. · El body puede ser un ubyte[] (de un inputstream, un cfile, etc) o un string
  12. · Si es un ubyte[] el get_body() devuelve el ubyte[] tal cual (leyendo del inputstream si es necesario)
  13. · Si es un string, el get_body() convierte el _charset indicado y se hace un cast a ubyte[] al devolver
  14. */
  15.  
  16. static immutable default_charset = "Latin-1";
  17.  
  18. class ResponseBody
  19. {
  20.     this(ubyte[] data)
  21.     {
  22.         _ubyte_content = data; // .dup? .idup?
  23.         _store_type = ContentStore.BYTEARRAY;
  24.     }  
  25.     this(string data)
  26.     {
  27.         _string_content = data;
  28.         _store_type = ContentStore.STRING;
  29.     }
  30.     this(InputStream istream)
  31.     {
  32.         _istream_content = istream;
  33.         _store_type = ContentStore.ISTREAM;
  34.     }
  35.     this()
  36.     {
  37.         _store_type = ContentStore.EMPTY;
  38.     }
  39.  
  40.     @property content(ubyte[] data)
  41.     {
  42.         _ubyte_content = data;
  43.         _store_type = ContentStore.BYTEARRAY;
  44.         // Clear the other _*_content members?
  45.     }
  46.  
  47.     @property content(string data)
  48.     {
  49.         _string_content = data;
  50.         _store_type = ContentStore.STRING;
  51.     }
  52.  
  53.     @property content(InputStream istream)
  54.     {
  55.         _istream_content = istream;
  56.         _store_type = ContentStore.ISTREAM;
  57.     }
  58.  
  59.     ubyte[] get_content_as_bytes(string charset = default_charset)
  60.     {
  61.         ubyte[] output;
  62.  
  63.         // No conversion is done if read from a file or inputstream, the user should take care of that if needed
  64.         if (_store_type == ContentStore.EMPTY)
  65.             return output; // Throw exception instead?
  66.  
  67.         else if (_store_type == ContentStore.BYTEARRAY)
  68.             output = _ubyte_content;
  69.  
  70.         else if (_store_type == ContentStore.STRING) {
  71.             string charset_simp = charset.tolower().removechars("-");
  72.             // is a string, encode into the specified encoding
  73.             if (charset_simp == "utf8")
  74.                 output = cast(ubyte[])_string_content;
  75.  
  76.             if (charset_simp == "ascii") {
  77.                 AsciiString s;
  78.                 transcode(_string_content, s);
  79.                 output = cast(ubyte[]) s;
  80.             }
  81.             else if (charset_simp == "latin1") {
  82.                 Latin1String s;
  83.                 transcode(_string_content, s);
  84.                 output = cast(ubyte[]) s;
  85.             }
  86.             else if (charset_simp == "utf16") {
  87.                 wstring s;
  88.                 transcode(_string_content, s);
  89.                 output = cast(ubyte[]) s;
  90.             }
  91.             else if (charset_simp == "utf32") {
  92.                 dstring s;
  93.                 transcode(_string_content, s);
  94.                 output = cast(ubyte[]) s;
  95.             }
  96.             else
  97.                 throw new Exception("Encoding " ~ charset ~ " is not supported");
  98.         }
  99.  
  100.         // XXX TEST
  101.         else if (_store_type == ContentStore.ISTREAM) {
  102.             ubyte[1024] partial;
  103.             output.length = 1024*128;
  104.  
  105.             uint readed, totalread;
  106.             while ((readed = _istream_content.read(partial)) > 0) {
  107.                 if (output.length < totalread+readed)
  108.                     output.length *= 2;
  109.                 //output ~= partial[0..readed];
  110.                 output[totalread..totalread+readed] = partial[0..readed];
  111.                 totalread += readed;
  112.             }
  113.             output.length = totalread;
  114.         }
  115.            
  116.         return output;
  117.     }
  118.  
  119.     // XXX TEST
  120.     InputStream get_content_as_istream() {
  121.         if (_store_type == ContentStore.EMPTY) {
  122.             ubyte[] empty;
  123.             return new MemoryStream(empty); // Throw exception instead?
  124.         }
  125.  
  126.         else if (_store_type == ContentStore.BYTEARRAY)
  127.             return new MemoryStream(get_content_as_bytes());
  128.  
  129.         else if (_store_type == ContentStore.STRING)
  130.             return new MemoryStream( to!(char[])(_string_content) );
  131.  
  132.         else if (_store_type == ContentStore.ISTREAM)
  133.             return _istream_content;
  134.  
  135.         assert(0);
  136.     }
  137.  
  138.     private:
  139.         InputStream _istream_content;
  140.         ubyte[] _ubyte_content;
  141.         string _string_content;
  142.         enum ContentStore { EMPTY, STRING, BYTEARRAY, ISTREAM };
  143.         ContentStore _store_type = ContentStore.STRING;
  144.  
  145. }
  146.  
  147. ubyte[] byte_array_encoded_in(string input, string encoding) {
  148.     auto output = EncodingScheme.create(encoding);
  149.     writeln(typeid(output));
  150.     writeln(output);
  151.     //transcode(input, output);
  152.     //return cast(ubyte[]) output;
  153.     ubyte[] a;
  154.     return a;
  155. }
  156.  
  157. // convertir en unittest
  158. void main() {
  159.  
  160.     ubyte[] bytearray = cast(ubyte[]) (cast(Latin1String)"Esto es un fichero de texto con codificación Latin1");
  161.     string ascii_chars_in_utf = "En un lugar de la mancha";
  162.     string latin1_chars_in_utf = "ñaña";
  163.  
  164.     // ubyte[] input, utf-8 output
  165.     auto b = new ResponseBody(bytearray);
  166.     ubyte[] bodybytes = b.get_content_as_bytes("utf-8");
  167.     assert(cast(string)bodybytes == bytearray);
  168.  
  169.     // utf-8 input, ascii output
  170.     auto a = new ResponseBody(ascii_chars_in_utf);
  171.     bodybytes = a.get_content_as_bytes("ascii");
  172.     AsciiString ascii_chars;
  173.     transcode(ascii_chars_in_utf, ascii_chars);
  174.     assert(cast(AsciiString)bodybytes == ascii_chars);
  175.  
  176.     // utf-8 input, latin1 output
  177.     auto l = new ResponseBody(latin1_chars_in_utf);
  178.     bodybytes = l.get_content_as_bytes("latin-1");
  179.     Latin1String latin1_chars;
  180.     transcode(latin1_chars_in_utf, latin1_chars);
  181.     assert(cast(Latin1String)bodybytes == latin1_chars);
  182.  
  183.     // utf-8 input, utf-16 output
  184.     auto w = new ResponseBody("ñaña w16");
  185.     bodybytes = w.get_content_as_bytes("utf-16");
  186.     assert(cast(wstring)bodybytes == "ñaña w16"w);
  187.  
  188.     // utf-8 input, utf-32 output
  189.     auto d = new ResponseBody("ñaña w32");
  190.     bodybytes = d.get_content_as_bytes("utf-32");
  191.     assert(cast(dstring)bodybytes == "ñaña w32"d);
  192.    
  193. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement