authorgravatar for kappaloris@gmail.comLoris Cro <kappaloris@gmail.com> 2025-06-14 00:31:29+02:00
committergravatar for noreply@github.comGitHub <noreply@github.com> 2025-06-13 22:31:29+00:00
log180e8442af0c29924e021aed327bb4070665af65
treea86d459db3355833525a86d0181effeac69b83d7
parenta74119ac49230a40012c0dd979e4c35eefcfd66a
signaturebadge-check Signed by PGP key B5690EEEBB952194

zig init: simplify templating logic (#24170)

and also rename `advancedPrint` to `bufferedPrint` in the zig init templates These are left overs from my previous changes to zig init. The new templating system removes LITNAME because the new restrictions on package names make it redundant with NAME, and the use of underscores for marking templated identifiers lets us template variable names while still keeping zig fmt happy.

5 files changed, 22 insertions(+), 28 deletions(-)

lib/init/build.zig+5-5
...@@ -29,7 +29,7 @@ pub fn build(b: *std.Build) void {...@@ -29,7 +29,7 @@ pub fn build(b: *std.Build) void {
29 // to our consumers. We must give it a name because a Zig package can expose29 // to our consumers. We must give it a name because a Zig package can expose
30 // multiple modules and consumers will need to be able to specify which30 // multiple modules and consumers will need to be able to specify which
31 // module they want to access.31 // module they want to access.
32 const mod = b.addModule(".NAME", .{32 const mod = b.addModule("_NAME", .{
33 // The root source file is the "entry point" of this module. Users of33 // The root source file is the "entry point" of this module. Users of
34 // this module will only be able to access public declarations contained34 // this module will only be able to access public declarations contained
35 // in this file, which means that if you have declarations that you35 // in this file, which means that if you have declarations that you
...@@ -59,7 +59,7 @@ pub fn build(b: *std.Build) void {...@@ -59,7 +59,7 @@ pub fn build(b: *std.Build) void {
59 // If neither case applies to you, feel free to delete the declaration you59 // If neither case applies to you, feel free to delete the declaration you
60 // don't need and to put everything under a single module.60 // don't need and to put everything under a single module.
61 const exe = b.addExecutable(.{61 const exe = b.addExecutable(.{
62 .name = ".NAME",62 .name = "_NAME",
63 .root_module = b.createModule(.{63 .root_module = b.createModule(.{
64 // b.createModule defines a new module just like b.addModule but,64 // b.createModule defines a new module just like b.addModule but,
65 // unlike b.addModule, it does not expose the module to consumers of65 // unlike b.addModule, it does not expose the module to consumers of
...@@ -74,12 +74,12 @@ pub fn build(b: *std.Build) void {...@@ -74,12 +74,12 @@ pub fn build(b: *std.Build) void {
74 // List of modules available for import in source files part of the74 // List of modules available for import in source files part of the
75 // root module.75 // root module.
76 .imports = &.{76 .imports = &.{
77 // Here ".NAME" is the name you will use in your source code to77 // Here "_NAME" is the name you will use in your source code to
78 // import this module (e.g. `@import(".NAME")`). The name is78 // import this module (e.g. `@import("_NAME")`). The name is
79 // repeated because you are allowed to rename your imports, which79 // repeated because you are allowed to rename your imports, which
80 // can be extremely useful in case of collisions (which can happen80 // can be extremely useful in case of collisions (which can happen
81 // importing modules from different packages).81 // importing modules from different packages).
82 .{ .name = ".NAME", .module = mod },82 .{ .name = "_NAME", .module = mod },
83 },83 },
84 }),84 }),
85 });85 });
lib/init/build.zig.zon+2-2
...@@ -6,7 +6,7 @@...@@ -6,7 +6,7 @@
6 //6 //
7 // It is redundant to include "zig" in this name because it is already7 // It is redundant to include "zig" in this name because it is already
8 // within the Zig package namespace.8 // within the Zig package namespace.
9 .name = .LITNAME,9 .name = ._NAME,
10 // This is a [Semantic Version](https://semver.org/).10 // This is a [Semantic Version](https://semver.org/).
11 // In a future version of Zig it will be used for package deduplication.11 // In a future version of Zig it will be used for package deduplication.
12 .version = "0.0.0",12 .version = "0.0.0",
...@@ -25,7 +25,7 @@...@@ -25,7 +25,7 @@
25 .fingerprint = .FINGERPRINT, // Changing this has security and trust implications.25 .fingerprint = .FINGERPRINT, // Changing this has security and trust implications.
26 // Tracks the earliest Zig version that the package considers to be a26 // Tracks the earliest Zig version that the package considers to be a
27 // supported use case.27 // supported use case.
28 .minimum_zig_version = ".ZIGVER",28 .minimum_zig_version = "_ZIGVER",
29 // This field is optional.29 // This field is optional.
30 // Each dependency must either provide a `url` and `hash`, or a `path`.30 // Each dependency must either provide a `url` and `hash`, or a `path`.
31 // `zig build --fetch` can be used to fetch all dependencies of a package, recursively.31 // `zig build --fetch` can be used to fetch all dependencies of a package, recursively.
lib/init/src/main.zig+2-2
...@@ -1,10 +1,10 @@...@@ -1,10 +1,10 @@
1const std = @import("std");1const std = @import("std");
2const _LITNAME = @import(".NAME");2const _NAME = @import(".NAME");
33
4pub fn main() !void {4pub fn main() !void {
5 // Prints to stderr, ignoring potential errors.5 // Prints to stderr, ignoring potential errors.
6 std.debug.print("All your {s} are belong to us.\n", .{"codebase"});6 std.debug.print("All your {s} are belong to us.\n", .{"codebase"});
7 try .NAME.advancedPrint();7 try _NAME.bufferedPrint();
8}8}
99
10test "simple test" {10test "simple test" {
lib/init/src/root.zig+2-1
...@@ -1,11 +1,12 @@...@@ -1,11 +1,12 @@
1//! By convention, root.zig is the root source file when making a library.1//! By convention, root.zig is the root source file when making a library.
2const std = @import("std");2const std = @import("std");
33
4pub fn advancedPrint() !void {4pub fn bufferedPrint() !void {
5 // Stdout is for the actual output of your application, for example if you5 // Stdout is for the actual output of your application, for example if you
6 // are implementing gzip, then only the compressed bytes should be sent to6 // are implementing gzip, then only the compressed bytes should be sent to
7 // stdout, not any debugging messages.7 // stdout, not any debugging messages.
8 const stdout_file = std.io.getStdOut().writer();8 const stdout_file = std.io.getStdOut().writer();
9 // Buffering can improve performance significantly in print-heavy programs.
9 var bw = std.io.bufferedWriter(stdout_file);10 var bw = std.io.bufferedWriter(stdout_file);
10 const stdout = bw.writer();11 const stdout = bw.writer();
1112
src/main.zig+11-18
...@@ -7290,34 +7290,27 @@ const Templates = struct {...@@ -7290,34 +7290,27 @@ const Templates = struct {
7290 new_line = false;7290 new_line = false;
7291 }7291 }
7292 }7292 }
7293
7293 if (templates.strip and contents[i] == '\n') {7294 if (templates.strip and contents[i] == '\n') {
7294 new_line = true;7295 new_line = true;
7295 } else if (contents[i] == '_') {7296 } else if (contents[i] == '_' or contents[i] == '.') {
7296 if (std.mem.startsWith(u8, contents[i..], "_LITNAME")) {7297 // Both '_' and '.' are allowed because depending on the context
7297 try templates.buffer.appendSlice(root_name);7298 // one prefix will be valid, while the other might not.
7298 i += "_LITNAME".len;7299 if (std.mem.startsWith(u8, contents[i + 1 ..], "NAME")) {
7299 continue;
7300 }
7301 } else if (contents[i] == '.') {
7302 if (std.mem.startsWith(u8, contents[i..], ".LITNAME")) {
7303 try templates.buffer.append('.');
7304 try templates.buffer.appendSlice(root_name);7300 try templates.buffer.appendSlice(root_name);
7305 i += ".LITNAME".len;7301 i += "_NAME".len;
7306 continue;7302 continue;
7307 } else if (std.mem.startsWith(u8, contents[i..], ".NAME")) {7303 } else if (std.mem.startsWith(u8, contents[i + 1 ..], "FINGERPRINT")) {
7308 try templates.buffer.appendSlice(root_name);
7309 i += ".NAME".len;
7310 continue;
7311 } else if (std.mem.startsWith(u8, contents[i..], ".FINGERPRINT")) {
7312 try templates.buffer.writer().print("0x{x}", .{fingerprint.int()});7304 try templates.buffer.writer().print("0x{x}", .{fingerprint.int()});
7313 i += ".FINGERPRINT".len;7305 i += "_FINGERPRINT".len;
7314 continue;7306 continue;
7315 } else if (std.mem.startsWith(u8, contents[i..], ".ZIGVER")) {7307 } else if (std.mem.startsWith(u8, contents[i + 1 ..], "ZIGVER")) {
7316 try templates.buffer.appendSlice(build_options.version);7308 try templates.buffer.appendSlice(build_options.version);
7317 i += ".ZIGVER".len;7309 i += "_ZIGVER".len;
7318 continue;7310 continue;
7319 }7311 }
7320 }7312 }
7313
7321 try templates.buffer.append(contents[i]);7314 try templates.buffer.append(contents[i]);
7322 i += 1;7315 i += 1;
7323 }7316 }