Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
kristoff-it committed Oct 8, 2024
1 parent 9d95313 commit dd5d3eb
Show file tree
Hide file tree
Showing 5 changed files with 201 additions and 32 deletions.
3 changes: 1 addition & 2 deletions build.zig.zon
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,7 @@
.hash = "122014e78d7c69d93595993b3231f3141368e22634b332b0b91a2fb73a8570f147a5",
},
.superhtml = .{
.url = "git+https://github.com/kristoff-it/superhtml#3edb67236291d45ba97a79cdac3b91692487a352",
.hash = "1220879d0db55e043907b1af7623d93c6be80f27e3af75e35c85fa85e3823f52c922",
.path = "../superhtml",
},
.ziggy = .{
.url = "git+https://github.com/kristoff-it/ziggy#c66f47bc632c66668d61fa06eda112b41d6e5130",
Expand Down
33 changes: 15 additions & 18 deletions src/context.zig
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ pub const Map = @import("context/Map.zig");
// pub const Slice = @import("context/Slice.zig");
pub const Optional = @import("context/Optional.zig");
pub const Iterator = @import("context/Iterator.zig");
pub const Array = @import("context/Array.zig");

pub const Value = union(enum) {
template: *const Template,
Expand All @@ -93,6 +94,7 @@ pub const Value = union(enum) {
int: Int,
float: Float,
iterator: *context.Iterator,
array: Array,
map_kv: Map.KV,
err: []const u8,

Expand Down Expand Up @@ -145,9 +147,10 @@ pub const Value = union(enum) {
.integer => |i| return .{ .int = .{ .value = i } },
.bytes => |s| return .{ .string = .{ .value = s } },
.array => |a| return .{
.iterator = try context.Iterator.init(gpa, .{
.dynamic_it = .{ .items = a },
}),
.iterator = try Value.Iterator.fromArray(
gpa,
(try Array.init(gpa, ziggy.dynamic.Value, a)).array,
),
},
.tag => |t| {
std.debug.assert(std.mem.eql(u8, t.name, "date"));
Expand Down Expand Up @@ -197,22 +200,16 @@ pub const Value = union(enum) {
.iterator = opt,
} else .{ .err = "$loop is not set" },
*context.Iterator => .{ .iterator = v },
[]const []const u8 => .{
.iterator = try context.Iterator.init(gpa, .{
.string_it = .{ .items = v },
}),
},
[]const []const u8 => try Array.init(gpa, []const u8, v),

[]const Page.Alternative => .{
.iterator = try context.Iterator.init(gpa, .{
.alt_it = .{ .items = v },
}),
},
[]Page.ContentSection => .{
.iterator = try context.Iterator.init(gpa, .{
.content_it = .{ .items = v },
}),
},
// .{
// .iterator = try context.Iterator.init(gpa, .{
// .string_it = .{ .items = v },
// }),
// },

[]const Page.Alternative => try Array.init(gpa, Page.Alternative, v),
[]Page.ContentSection => try Array.init(gpa, Page.ContentSection, v),
else => @compileError("TODO: implement Value.from for " ++ @typeName(@TypeOf(v))),
};
}
Expand Down
170 changes: 170 additions & 0 deletions src/context/Array.zig
Original file line number Diff line number Diff line change
@@ -0,0 +1,170 @@
const Array = @This();

const std = @import("std");
const ziggy = @import("ziggy");
const superhtml = @import("superhtml");
const scripty = @import("scripty");
const context = @import("../context.zig");
const doctypes = @import("doctypes.zig");
const Signature = doctypes.Signature;
const Allocator = std.mem.Allocator;
const Value = context.Value;
const Template = context.Template;
const Site = context.Site;
const Page = context.Page;
const Map = context.Map;

len: usize,
empty: bool,
_items: []const Value,

pub fn init(gpa: Allocator, T: type, items: []const T) error{OutOfMemory}!Value {
if (T == Value) return .{
.array = .{
.len = items.len,
.empty = items.len == 0,
._items = items,
},
};

const boxed_items = try gpa.alloc(Value, items.len);

for (items, boxed_items) |i, *bi| {
bi.* = try Value.from(gpa, i);
}

return .{
.array = .{
.len = items.len,
.empty = items.len == 0,
._items = boxed_items,
},
};
}

// pub fn deinit(iter: *const Iterator, gpa: Allocator) void {
// gpa.destroy(iter);
// }

pub const dot = scripty.defaultDot(Array, Value, false);
pub const description = "An array of items.";
pub const Fields = struct {
pub const len =
\\The length of the array.
;
pub const empty =
\\True when len is 0.
;
};

pub const Builtins = struct {
pub const slice = struct {
pub const signature: Signature = .{
.params = &.{ .Int, .{ .Opt = .Int } },
.ret = .Array,
};
pub const description =
\\Slices an array from the first value (inclusive) to the
\\second value (exclusive).
\\
\\The second value can be omitted and defaults to the array's
\\length, meaning that invoking `slice` with one argunent
\\produces **suffixes** of the original sequence (i.e. it
\\removes a prefix from the original sequence).
\\
\\Note that negative values are not allowed at the moment.
;
pub const examples =
\\$page.tags.slice(0,1)
;
pub fn call(
arr: Array,
gpa: Allocator,
args: []const Value,
) !Value {
const bad_arg = .{ .err = "expected 1 or 2 integer argument(s)" };
if (args.len < 1 or args.len > 2) return bad_arg;

const start = switch (args[0]) {
.int => |i| i.value,
else => return bad_arg,
};
const end: i64 = if (args.len == 1) @intCast(arr.len) else switch (args[1]) {
.int => |i| i.value,
else => return bad_arg,
};

if (start < 0) return Value.errFmt(
gpa,
"start value {} is negative",
.{start},
);

if (end < 0) return Value.errFmt(
gpa,
"end value {} is negative",
.{end},
);

if (start >= arr.len) return Value.errFmt(gpa, "start value {} exceeds array of length {}", .{
start, arr.len,
});

if (end > arr.len) return Value.errFmt(gpa, "end value {} exceeds array of length {}", .{
end, arr.len,
});

if (start > end) return Value.errFmt(gpa, "start value {} is bigger than end value {}!", .{
start, end,
});

const new = arr._items[@intCast(start)..@intCast(end)];

return .{
.array = .{
.len = new.len,
.empty = new.len == 0,
._items = new,
},
};
}
};

pub const at = struct {
pub const signature: Signature = .{
.params = &.{.Int},
.ret = .Value,
};
pub const description =
\\Returns the value at the provided index.
;
pub const examples =
\\$page.tags.at(0)
;
pub fn call(
arr: Array,
gpa: Allocator,
args: []const Value,
) !Value {
const bad_arg = .{ .err = "expected 1 integer argument" };
if (args.len != 1) return bad_arg;

const idx = switch (args[0]) {
.int => |i| i.value,
else => return bad_arg,
};

if (idx < 0) return Value.errFmt(
gpa,
"index value {} is negative",
.{idx},
);

if (idx >= arr.len) return Value.errFmt(gpa, "index {} exceeds array of length {}", .{
idx, arr.len,
});

return arr._items[@intCast(idx)];
}
};
};
15 changes: 10 additions & 5 deletions src/context/Iterator.zig
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ const Template = context.Template;
const Site = context.Site;
const Page = context.Page;
const Map = context.Map;
const Array = context.Array;

it: Value = undefined,
idx: usize = 0,
Expand All @@ -24,14 +25,12 @@ _superhtml_context: superhtml.utils.IteratorContext(Value, Template) = .{},
_impl: Impl,

pub const Impl = union(enum) {
string_it: SliceIterator([]const u8),
page_it: PageIterator,
page_slice_it: SliceIterator(*const Page),
// page_slice_it: SliceIterator(*const Page),
translation_it: TranslationIterator,
alt_it: SliceIterator(Page.Alternative),
content_it: SliceIterator(Page.ContentSection),
map_it: MapIterator,
dynamic_it: SliceIterator(ziggy.dynamic.Value),
// dynamic_it: SliceIterator(ziggy.dynamic.Value),
value_it: SliceIterator(Value),

pub fn len(impl: Impl) usize {
switch (impl) {
Expand Down Expand Up @@ -63,6 +62,12 @@ pub fn next(iter: *Iterator, gpa: Allocator) !bool {
}
}

pub fn fromArray(gpa: Allocator, arr: Array) !*Iterator {
return init(gpa, .{
.value_it = .{ .items = arr._items },
});
}

pub const dot = scripty.defaultDot(Iterator, Value, false);
pub const description = "An iterator.";
pub const Fields = struct {
Expand Down
12 changes: 5 additions & 7 deletions src/context/Site.zig
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ const Signature = @import("doctypes.zig").Signature;
const Value = context.Value;
const Bool = context.Bool;
const String = context.String;
const Array = context.Array;

const log = std.log.scoped(.scripty);

Expand Down Expand Up @@ -239,8 +240,9 @@ pub const Builtins = struct {
.err = "expected at least 1 string argument",
};

const page_list = try gpa.alloc(*const context.Page, args.len);
const page_list = try gpa.alloc(Value, args.len);
errdefer gpa.free(page_list);

for (args, page_list) |a, *p| {
const ref = switch (a) {
.string => |s| s.value,
Expand All @@ -261,15 +263,11 @@ pub const Builtins = struct {
gpa.free(page_list);
return res;
},
.page => |_p| p.* = _p,
.page => |_p| p.* = .{ .page = _p },
else => unreachable,
}
}
return .{
.iterator = try context.Iterator.init(gpa, .{
.page_slice_it = .{ .items = page_list },
}),
};
return Array.init(gpa, Value, page_list);
}
};
pub const locale = struct {
Expand Down

0 comments on commit dd5d3eb

Please sign in to comment.