aboutsummaryrefslogtreecommitdiff
path: root/src/string_immutable.zig
diff options
context:
space:
mode:
authorGravatar Jarred Sumner <jarred@jarredsumner.com> 2023-02-13 00:50:15 -0800
committerGravatar GitHub <noreply@github.com> 2023-02-13 00:50:15 -0800
commitaa0762e4660bb17b86890b923368e5a0dc8daf7b (patch)
treea134621368f9def9a85473e90a6189afb956b457 /src/string_immutable.zig
parentcdbc620104b939f7112fa613ca192e5fe6e02a7d (diff)
downloadbun-aa0762e4660bb17b86890b923368e5a0dc8daf7b.tar.gz
bun-aa0762e4660bb17b86890b923368e5a0dc8daf7b.tar.zst
bun-aa0762e4660bb17b86890b923368e5a0dc8daf7b.zip
Implement `FormData` (#2051)
* Backport std::forward change * Implement `FormData` * Fix io_darwin headers issue * Implement `Blob` support in FormData * Add test for file upload * Fix bug with Blob not reading Content-Type * Finish implementing FormData * Add FormData to types --------- Co-authored-by: Jarred Sumner <709451+Jarred-Sumner@users.noreply.github.com>
Diffstat (limited to 'src/string_immutable.zig')
-rw-r--r--src/string_immutable.zig50
1 files changed, 50 insertions, 0 deletions
diff --git a/src/string_immutable.zig b/src/string_immutable.zig
index 079817362..9d36d0c78 100644
--- a/src/string_immutable.zig
+++ b/src/string_immutable.zig
@@ -178,6 +178,56 @@ pub inline fn indexOf(self: string, str: string) ?usize {
return @ptrToInt(start) - @ptrToInt(self_ptr);
}
+pub fn split(self: string, delimiter: string) SplitIterator {
+ return SplitIterator{
+ .buffer = self,
+ .index = 0,
+ .delimiter = delimiter,
+ };
+}
+
+pub const SplitIterator = struct {
+ buffer: []const u8,
+ index: ?usize,
+ delimiter: []const u8,
+
+ const Self = @This();
+
+ /// Returns a slice of the first field. This never fails.
+ /// Call this only to get the first field and then use `next` to get all subsequent fields.
+ pub fn first(self: *Self) []const u8 {
+ std.debug.assert(self.index.? == 0);
+ return self.next().?;
+ }
+
+ /// Returns a slice of the next field, or null if splitting is complete.
+ pub fn next(self: *Self) ?[]const u8 {
+ const start = self.index orelse return null;
+ const end = if (indexOf(self.buffer[start..], self.delimiter)) |delim_start| blk: {
+ const del = delim_start + start;
+ self.index = del + self.delimiter.len;
+ break :blk delim_start + start;
+ } else blk: {
+ self.index = null;
+ break :blk self.buffer.len;
+ };
+
+ return self.buffer[start..end];
+ }
+
+ /// Returns a slice of the remaining bytes. Does not affect iterator state.
+ pub fn rest(self: Self) []const u8 {
+ const end = self.buffer.len;
+ const start = self.index orelse end;
+ return self.buffer[start..end];
+ }
+
+ /// Resets the iterator to the initial slice.
+ pub fn reset(self: *Self) void {
+ self.index = 0;
+ }
+};
+
// --
// This is faster when the string is found, by about 2x for a 8 MB file.
// It is slower when the string is NOT found