1 module nxt.byline;
2 
3 /** Type of NewLine Encoding.
4  */
5 enum Newline
6 {
7     any,                        // Any of win, mac or unix
8     win,                        // Windows: "\r\n"
9     mac,                        // Mac OS: '\r'
10     unix,                       // UNIX/Linux: '\n'
11     native,                     // Current OS decides: '\n'
12 }
13 
14 /** Split Input by line.
15  *
16  * See_Also: http://forum.dlang.org/thread/fjqpdfzmitcxxzpwlbgb@forum.dlang.org#post-rwxrytxqqurrazifugje:40forum.dlang.org
17  *
18  * TODO: This should fail with better error message:
19  * assert(equal((cast(ubyte[])"a\nb").byLine!(Newline.any), ["a", "b"]));
20  */
21 auto byLine(Newline nl = Newline.any, Range)(Range input)
22 if (is(typeof(Range.init[0 .. 0])) && // can be sliced
23     is(typeof(Range.init[0]) : char))
24 {
25     import nxt.splitter_ex : splitterASCIIAmong;
26     static if (nl == Newline.native)
27     {
28         version (Windows)
29             return input.splitterASCIIAmong!('\r', '\n');
30         else version (Posix)
31             return input.splitterASCIIAmong!('\n');
32         else
33             static assert(0, "Neither on Windows nor Posix!");
34     }
35     else
36     {
37         static if (nl == Newline.unix)
38             return input.splitterASCIIAmong!('\n');
39         else static if (nl == Newline.win)
40             return input.splitterASCIIAmong!('\r', '\n');
41         else static if (nl == Newline.mac)
42             return input.splitterASCIIAmong!('\r');
43         else static if (nl == Newline.any)
44             return input.splitterASCIIAmong!('\r', '\n');
45         else
46             static assert(0, "Handle Newline." ~ nl.stringof);
47     }
48 }
49 
50 ///
51 @safe pure nothrow @nogc unittest
52 {
53     import std.algorithm.comparison: equal;
54     assert(equal("a\nb".byLine!(Newline.native), ["a", "b"].s[]));
55     assert(equal("a\r\nb".byLine!(Newline.win), ["a", "b"].s[]));
56     assert(equal("a\rb".byLine!(Newline.mac), ["a", "b"].s[]));
57     assert(equal("a\nb".byLine!(Newline.unix), ["a", "b"].s[]));
58     assert(equal("a\nb".byLine!(Newline.any), ["a", "b"].s[]));
59 }
60 
61 version(unittest)
62 {
63     import nxt.array_help : s;
64 }