@robbeverhelst/do 1.69.0 → 1.71.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/README.md +1 -1
  2. package/dist/do.js +118 -52
  3. package/package.json +1 -1
package/README.md CHANGED
@@ -16,7 +16,7 @@ bunx @robbeverhelst/do today
16
16
 
17
17
  The daily loop, all over `/api/v1` with an API key — no destructive verbs:
18
18
 
19
- - `capture "<text> #tag !priority"` — quick-add a task to the inbox
19
+ - `capture "<text> #tag ! ~area"` — quick-add a task to the inbox (`!` stars it)
20
20
  - `today` — actionable tasks (overdue / scheduled / due / in-progress)
21
21
  - `task done <id>` — complete (idempotent)
22
22
  - `task snooze <id> [--days N | --until <date>]` — reschedule
package/dist/do.js CHANGED
@@ -2762,6 +2762,9 @@ class Index {
2762
2762
  function index(name) {
2763
2763
  return new IndexBuilderOn(false, name);
2764
2764
  }
2765
+ function uniqueIndex(name) {
2766
+ return new IndexBuilderOn(true, name);
2767
+ }
2765
2768
 
2766
2769
  // ../../node_modules/drizzle-orm/pg-core/primary-keys.js
2767
2770
  function primaryKey(...config) {
@@ -4374,7 +4377,6 @@ var userSettings = pgTable("user_settings", {
4374
4377
 
4375
4378
  // ../../packages/schema/src/db/domain.ts
4376
4379
  var taskStatus = pgEnum("task_status", ["todo", "in_progress", "done", "cancelled"]);
4377
- var taskPriority = pgEnum("task_priority", ["none", "low", "medium", "high"]);
4378
4380
  var habitMeasurementType = pgEnum("habit_measurement_type", [
4379
4381
  "binary",
4380
4382
  "quantitative",
@@ -4398,7 +4400,7 @@ var tasks = pgTable("tasks", {
4398
4400
  tenantId: text("tenant_id").notNull().references(() => tenants.id),
4399
4401
  notes: text("notes"),
4400
4402
  status: taskStatus("status").notNull().default("todo"),
4401
- priority: taskPriority("priority").notNull().default("none"),
4403
+ starred: boolean("starred").notNull().default(false),
4402
4404
  allDay: boolean("all_day").notNull().default(true),
4403
4405
  scheduledAt: timestamp("scheduled_at", { withTimezone: true }),
4404
4406
  startAt: timestamp("start_at", { withTimezone: true }),
@@ -4501,6 +4503,20 @@ var pushSubscriptions = pgTable("push_subscriptions", {
4501
4503
  auth: text("auth").notNull(),
4502
4504
  createdAt: timestamp("created_at", { withTimezone: true }).notNull().defaultNow()
4503
4505
  }, (t) => [unique("push_subscriptions_endpoint_uniq").on(t.endpoint)]);
4506
+ // ../../packages/schema/src/db/products.ts
4507
+ var products = pgTable("products", {
4508
+ id: text("id").primaryKey(),
4509
+ tenantId: text("tenant_id").notNull().references(() => tenants.id),
4510
+ name: text("name").notNull(),
4511
+ normalizedName: text("normalized_name").notNull(),
4512
+ category: text("category"),
4513
+ baseUnit: text("base_unit"),
4514
+ conversions: jsonb("conversions").$type().notNull().default({}),
4515
+ createdAt: timestamp("created_at", { withTimezone: true }).notNull().defaultNow()
4516
+ }, (t) => [
4517
+ uniqueIndex("products_tenant_name_key").on(t.tenantId, t.normalizedName),
4518
+ index("products_tenant_idx").on(t.tenantId)
4519
+ ]);
4504
4520
  // ../../packages/schema/src/db/shopping.ts
4505
4521
  var shoppingLists = pgTable("shopping_lists", {
4506
4522
  id: text("id").primaryKey().references(() => nodes.id),
@@ -4520,6 +4536,7 @@ var shoppingItems = pgTable("shopping_items", {
4520
4536
  tenantId: text("tenant_id").notNull().references(() => tenants.id),
4521
4537
  listId: text("list_id").notNull().references(() => shoppingLists.id),
4522
4538
  title: text("title").notNull(),
4539
+ productId: text("product_id").references(() => products.id),
4523
4540
  quantity: doublePrecision("quantity"),
4524
4541
  unit: text("unit"),
4525
4542
  isChecked: boolean("is_checked").notNull().default(false),
@@ -4530,12 +4547,14 @@ var shoppingItems = pgTable("shopping_items", {
4530
4547
  createdAt: timestamp("created_at", { withTimezone: true }).notNull().defaultNow()
4531
4548
  }, (t) => [
4532
4549
  index("shopping_items_list_order_idx").on(t.listId, t.sortOrder),
4533
- index("shopping_items_tenant_idx").on(t.tenantId)
4550
+ index("shopping_items_tenant_idx").on(t.tenantId),
4551
+ index("shopping_items_product_idx").on(t.productId)
4534
4552
  ]);
4535
4553
  // ../../packages/schema/src/db/inventory.ts
4536
4554
  var inventoryItems = pgTable("inventory_items", {
4537
4555
  id: text("id").primaryKey().references(() => nodes.id),
4538
4556
  tenantId: text("tenant_id").notNull().references(() => tenants.id),
4557
+ productId: text("product_id").references(() => products.id),
4539
4558
  quantity: doublePrecision("quantity").notNull().default(0),
4540
4559
  unit: text("unit"),
4541
4560
  category: text("category"),
@@ -4545,7 +4564,8 @@ var inventoryItems = pgTable("inventory_items", {
4545
4564
  notes: text("notes"),
4546
4565
  facet: jsonb("facet").$type()
4547
4566
  }, (t) => [
4548
- index("inventory_items_tenant_idx").on(t.tenantId)
4567
+ index("inventory_items_tenant_idx").on(t.tenantId),
4568
+ index("inventory_items_product_idx").on(t.productId)
4549
4569
  ]);
4550
4570
  // ../../packages/schema/src/db/collection.ts
4551
4571
  var collectionItems = pgTable("collection_items", {
@@ -4597,13 +4617,15 @@ var recipeIngredients = pgTable("recipe_ingredients", {
4597
4617
  tenantId: text("tenant_id").notNull().references(() => tenants.id),
4598
4618
  recipeId: text("recipe_id").notNull().references(() => recipes.id),
4599
4619
  name: text("name").notNull(),
4620
+ productId: text("product_id").references(() => products.id),
4600
4621
  quantity: doublePrecision("quantity"),
4601
4622
  unit: text("unit"),
4602
4623
  sortOrder: integer("sort_order").notNull().default(0),
4603
4624
  createdAt: timestamp("created_at", { withTimezone: true }).notNull().defaultNow()
4604
4625
  }, (t) => [
4605
4626
  index("recipe_ingredients_recipe_order_idx").on(t.recipeId, t.sortOrder),
4606
- index("recipe_ingredients_tenant_idx").on(t.tenantId)
4627
+ index("recipe_ingredients_tenant_idx").on(t.tenantId),
4628
+ index("recipe_ingredients_product_idx").on(t.productId)
4607
4629
  ]);
4608
4630
  var mealPlans = pgTable("meal_plans", {
4609
4631
  id: text("id").primaryKey().references(() => nodes.id),
@@ -5064,6 +5086,22 @@ var insightsHabitStreaks = pgView("insights_habit_streaks", {
5064
5086
  latestRunLength: integer("latest_run_length").notNull(),
5065
5087
  latestRunEnd: date("latest_run_end").notNull()
5066
5088
  }).existing();
5089
+ var insightsFindings = pgTable("insights_findings", {
5090
+ id: text("id").primaryKey(),
5091
+ tenantId: text("tenant_id").notNull().references(() => tenants.id, { onDelete: "cascade" }),
5092
+ kind: text("kind").notNull(),
5093
+ subject: text("subject").notNull(),
5094
+ entityId: text("entity_id"),
5095
+ sentence: text("sentence").notNull(),
5096
+ metrics: jsonb("metrics").$type().notNull(),
5097
+ confidence: text("confidence").notNull(),
5098
+ sampleSize: integer("sample_size").notNull(),
5099
+ effectSize: doublePrecision("effect_size").notNull(),
5100
+ windowDays: integer("window_days").notNull(),
5101
+ generatedAt: timestamp("generated_at", { withTimezone: true }).notNull().defaultNow()
5102
+ }, (t) => [
5103
+ index("insights_findings_tenant_idx").on(t.tenantId)
5104
+ ]);
5067
5105
  // ../../node_modules/zod/v4/classic/external.js
5068
5106
  var exports_external = {};
5069
5107
  __export(exports_external, {
@@ -19677,7 +19715,6 @@ var areaColorSchema = exports_external.enum(areaColor.enumValues);
19677
19715
  var reviewCadenceSchema = exports_external.enum(reviewCadence.enumValues);
19678
19716
  var projectStatusSchema = exports_external.enum(projectStatus.enumValues);
19679
19717
  var taskStatusSchema = exports_external.enum(taskStatus.enumValues);
19680
- var taskPrioritySchema = exports_external.enum(taskPriority.enumValues);
19681
19718
  var routineKindSchema = exports_external.enum(routineKind.enumValues);
19682
19719
  var routineStepRefSchema = exports_external.enum(routineStepRef.enumValues);
19683
19720
  var routineRunStatusSchema = exports_external.enum(routineRunStatus.enumValues);
@@ -19790,7 +19827,7 @@ var updateTaskInputSchema = createUpdateSchema(tasks, {
19790
19827
  title: exports_external.string().min(1).optional(),
19791
19828
  parentId: ulidSchema.nullish()
19792
19829
  }).strict();
19793
- var taskListFilterSchema = exports_external.enum(["all", "unsorted"]);
19830
+ var taskListFilterSchema = exports_external.enum(["all", "unsorted", "starred"]);
19794
19831
  // ../../packages/schema/src/contracts/habits.ts
19795
19832
  var habitSchema = createSelectSchema(habits);
19796
19833
  var habitEntrySchema = createSelectSchema(habitEntries, {
@@ -19822,12 +19859,17 @@ var createHabitEntryInputSchema = createInsertSchema(habitEntries, {
19822
19859
  source: habitEntrySourceSchema.default("manual"),
19823
19860
  occurredAt: exports_external.coerce.date().optional()
19824
19861
  }).omit({ tenantId: true, habitId: true, createdAt: true });
19862
+ var habitStreakStateSchema = exports_external.enum(["active", "recovering", "broken"]);
19825
19863
  var habitStreakSchema = exports_external.object({
19826
19864
  current: exports_external.number().int().nonnegative(),
19827
19865
  longest: exports_external.number().int().nonnegative(),
19828
19866
  periodValue: exports_external.number(),
19829
19867
  periodTarget: exports_external.number(),
19830
- satisfiedToday: exports_external.boolean()
19868
+ satisfiedToday: exports_external.boolean(),
19869
+ completionRate: exports_external.number().min(0).max(1),
19870
+ state: habitStreakStateSchema,
19871
+ graceBudget: exports_external.number().int().nonnegative(),
19872
+ graceRemaining: exports_external.number().int().nonnegative()
19831
19873
  });
19832
19874
  var habitRoutineRefSchema = exports_external.object({
19833
19875
  id: ulidSchema,
@@ -20142,7 +20184,7 @@ var FEATURE_MODULES = [
20142
20184
  {
20143
20185
  key: "tasks",
20144
20186
  label: "Tasks",
20145
- description: "To-dos, due dates, and priorities.",
20187
+ description: "To-dos, due dates, and starred focus.",
20146
20188
  group: "Track",
20147
20189
  defaultEnabled: true
20148
20190
  },
@@ -20335,6 +20377,19 @@ var reviewDayStatSchema = exports_external.object({
20335
20377
  completedOccurrences: exports_external.number().int().nonnegative()
20336
20378
  });
20337
20379
  var reviewStatsSchema = exports_external.array(reviewDayStatSchema);
20380
+ // ../../packages/schema/src/contracts/products.ts
20381
+ var productConversionsSchema = exports_external.record(exports_external.string(), exports_external.number());
20382
+ var productSchema = createSelectSchema(products, {
20383
+ conversions: productConversionsSchema,
20384
+ createdAt: exports_external.coerce.date()
20385
+ });
20386
+ var createProductInputSchema = createInsertSchema(products, {
20387
+ id: ulidSchema,
20388
+ name: exports_external.string().min(1),
20389
+ category: exports_external.string().nullish(),
20390
+ baseUnit: exports_external.string().nullish(),
20391
+ conversions: productConversionsSchema.optional()
20392
+ }).omit({ tenantId: true, normalizedName: true, createdAt: true });
20338
20393
  // ../../packages/schema/src/contracts/shopping.ts
20339
20394
  var shoppingRecurrenceUnitSchema = exports_external.enum(["day", "week", "month"]);
20340
20395
  var shoppingListSchema = createSelectSchema(shoppingLists, {
@@ -20354,6 +20409,7 @@ var shoppingItemSchema = createSelectSchema(shoppingItems, {
20354
20409
  var shoppingItemInputSchema = createInsertSchema(shoppingItems, {
20355
20410
  id: ulidSchema,
20356
20411
  title: exports_external.string().min(1),
20412
+ productId: ulidSchema.nullish(),
20357
20413
  quantity: exports_external.number().positive().nullish(),
20358
20414
  unit: exports_external.string().nullish(),
20359
20415
  isChecked: exports_external.boolean().optional(),
@@ -20519,6 +20575,7 @@ var inventoryItemSchema = createSelectSchema(inventoryItems, {
20519
20575
  });
20520
20576
  var createInventoryItemInputSchema = createInsertSchema(inventoryItems, {
20521
20577
  id: ulidSchema,
20578
+ productId: ulidSchema.nullish(),
20522
20579
  quantity: exports_external.number().min(0).optional(),
20523
20580
  unit: exports_external.string().nullish(),
20524
20581
  category: exports_external.string().nullish(),
@@ -20533,6 +20590,7 @@ var createInventoryItemInputSchema = createInsertSchema(inventoryItems, {
20533
20590
  displayKind: inventoryDisplayKindSchema.optional()
20534
20591
  });
20535
20592
  var updateInventoryItemInputSchema = createUpdateSchema(inventoryItems, {
20593
+ productId: ulidSchema.nullish(),
20536
20594
  quantity: exports_external.number().min(0).optional(),
20537
20595
  unit: exports_external.string().nullish(),
20538
20596
  category: exports_external.string().nullish(),
@@ -20644,6 +20702,7 @@ var recipeIngredientSchema = createSelectSchema(recipeIngredients, {
20644
20702
  var recipeIngredientInputSchema = exports_external.object({
20645
20703
  id: ulidSchema,
20646
20704
  name: exports_external.string().min(1),
20705
+ productId: ulidSchema.nullish(),
20647
20706
  quantity: exports_external.number().positive().nullish(),
20648
20707
  unit: exports_external.string().nullish(),
20649
20708
  sortOrder: exports_external.number().int().min(0).optional()
@@ -21617,13 +21676,12 @@ var automationConditionSchema = exports_external.object({
21617
21676
  op: automationConditionOpSchema,
21618
21677
  value: exports_external.unknown().optional()
21619
21678
  }).strict();
21620
- var automationTaskPrioritySchema = exports_external.enum(["none", "low", "medium", "high"]);
21621
21679
  var automationActionSchema = exports_external.discriminatedUnion("type", [
21622
21680
  exports_external.object({
21623
21681
  type: exports_external.literal("create_task"),
21624
21682
  title: exports_external.string().min(1).max(200),
21625
21683
  notes: exports_external.string().max(2000).optional(),
21626
- priority: automationTaskPrioritySchema.optional()
21684
+ starred: exports_external.boolean().optional()
21627
21685
  }).strict(),
21628
21686
  exports_external.object({ type: exports_external.literal("complete_task") }).strict(),
21629
21687
  exports_external.object({
@@ -21799,9 +21857,29 @@ var insightsStreakSchema = exports_external.object({
21799
21857
  lastCheckin: exports_external.string(),
21800
21858
  currentStreak: exports_external.number().int().nonnegative()
21801
21859
  });
21860
+ var insightsConfidenceSchema = exports_external.enum(["low", "medium", "high"]);
21861
+ var insightsFindingKindSchema = exports_external.enum([
21862
+ "habit_consistency",
21863
+ "habit_average",
21864
+ "habit_correlation"
21865
+ ]);
21866
+ var insightsFindingSchema = exports_external.object({
21867
+ id: exports_external.string(),
21868
+ kind: insightsFindingKindSchema,
21869
+ sentence: exports_external.string(),
21870
+ subject: exports_external.string(),
21871
+ entityId: exports_external.string().nullable(),
21872
+ metrics: exports_external.record(exports_external.string(), exports_external.number()),
21873
+ confidence: insightsConfidenceSchema,
21874
+ sampleSize: exports_external.number().int().nonnegative(),
21875
+ effectSize: exports_external.number(),
21876
+ windowDays: exports_external.number().int().positive(),
21877
+ generatedAt: exports_external.coerce.date()
21878
+ });
21802
21879
  var insightsOverviewSchema = exports_external.object({
21803
21880
  generatedAt: exports_external.coerce.date(),
21804
21881
  windowDays: exports_external.number().int().positive(),
21882
+ findings: exports_external.array(insightsFindingSchema),
21805
21883
  activity: exports_external.array(insightsActivityPointSchema),
21806
21884
  correlations: exports_external.array(insightsCorrelationSchema),
21807
21885
  streaks: exports_external.array(insightsStreakSchema)
@@ -22017,20 +22095,8 @@ function addMonths(d, months) {
22017
22095
 
22018
22096
  // ../../packages/schema/src/capture.ts
22019
22097
  var TAG_RE = /(?:^|\s)#([\p{L}\p{N}][\p{L}\p{N}_-]*)/gu;
22020
- var PRIORITY_RE = /(?:^|\s)!([\p{L}]+)/gu;
22098
+ var STAR_RE = /(?:^|\s)!(star|flag|s|f)?(?=\s|$)/giu;
22021
22099
  var AREA_RE = /(?:^|\s)~([\p{L}\p{N}][\p{L}\p{N}_-]*)/gu;
22022
- var PRIORITY_ALIASES = {
22023
- none: "none",
22024
- n: "none",
22025
- low: "low",
22026
- l: "low",
22027
- med: "medium",
22028
- medium: "medium",
22029
- m: "medium",
22030
- high: "high",
22031
- h: "high",
22032
- hi: "high"
22033
- };
22034
22100
  function parseCapture(input, now) {
22035
22101
  const tags = [];
22036
22102
  for (const match of input.matchAll(TAG_RE)) {
@@ -22038,12 +22104,10 @@ function parseCapture(input, now) {
22038
22104
  if (tag && !tags.includes(tag))
22039
22105
  tags.push(tag);
22040
22106
  }
22041
- let priority;
22042
- for (const match of input.matchAll(PRIORITY_RE)) {
22043
- const token = match[1]?.toLowerCase();
22044
- const mapped = token ? PRIORITY_ALIASES[token] : undefined;
22045
- if (mapped)
22046
- priority = mapped;
22107
+ let starred;
22108
+ for (const _ of input.matchAll(STAR_RE)) {
22109
+ starred = true;
22110
+ break;
22047
22111
  }
22048
22112
  let area;
22049
22113
  for (const match of input.matchAll(AREA_RE)) {
@@ -22053,7 +22117,7 @@ function parseCapture(input, now) {
22053
22117
  break;
22054
22118
  }
22055
22119
  }
22056
- let stripped = blankMatches(input, [TAG_RE, PRIORITY_RE, AREA_RE]);
22120
+ let stripped = blankMatches(input, [TAG_RE, STAR_RE, AREA_RE]);
22057
22121
  const when = now ? parseWhen(stripped, now) : undefined;
22058
22122
  if (when) {
22059
22123
  for (const span of [...when.spans].sort((a, b) => b.start - a.start)) {
@@ -22064,7 +22128,7 @@ function parseCapture(input, now) {
22064
22128
  return {
22065
22129
  title,
22066
22130
  tags,
22067
- ...priority ? { priority } : {},
22131
+ ...starred ? { starred } : {},
22068
22132
  ...area ? { area } : {},
22069
22133
  ...when?.scheduledAt ? { scheduledAt: when.scheduledAt, allDay: when.allDay } : {},
22070
22134
  ...when?.recurrence ? { recurrence: when.recurrence } : {}
@@ -22554,7 +22618,7 @@ var automationPresets = [
22554
22618
  name: "Low stock \u2192 add to groceries",
22555
22619
  trigger: { entity: "inventory", action: "updated" },
22556
22620
  condition: { path: "value.lowStock", op: "eq", value: true },
22557
- action: { type: "create_task", title: "Restock low groceries", priority: "medium" }
22621
+ action: { type: "create_task", title: "Restock low groceries" }
22558
22622
  }
22559
22623
  ]
22560
22624
  }
@@ -22587,8 +22651,8 @@ var automationPresets = [
22587
22651
  {
22588
22652
  key: "auto-task-overdue-bump",
22589
22653
  entity: "automation",
22590
- name: "Task overdue \u2192 bump priority",
22591
- description: "When a task goes overdue, raise a high-priority follow-up.",
22654
+ name: "Task overdue \u2192 star a follow-up",
22655
+ description: "When a task goes overdue, create a starred follow-up.",
22592
22656
  icon: "\u23F0",
22593
22657
  color: "#f59e0b",
22594
22658
  category: "Automations",
@@ -22597,10 +22661,10 @@ var automationPresets = [
22597
22661
  {
22598
22662
  ref: "automation",
22599
22663
  kind: "automation",
22600
- name: "Task overdue \u2192 bump priority",
22664
+ name: "Task overdue \u2192 star a follow-up",
22601
22665
  trigger: { entity: "tasks", action: "updated" },
22602
22666
  condition: { path: "value.overdue", op: "eq", value: true },
22603
- action: { type: "create_task", title: "Reprioritise overdue task", priority: "high" }
22667
+ action: { type: "create_task", title: "Reprioritise overdue task", starred: true }
22604
22668
  }
22605
22669
  ]
22606
22670
  }
@@ -22644,8 +22708,7 @@ var automationPresets = [
22644
22708
  condition: { path: "value.status", op: "eq", value: "finished" },
22645
22709
  action: {
22646
22710
  type: "create_task",
22647
- title: "Rate the book you just finished",
22648
- priority: "low"
22711
+ title: "Rate the book you just finished"
22649
22712
  }
22650
22713
  }
22651
22714
  ]
@@ -24304,7 +24367,7 @@ function parseCapture2(input, now) {
24304
24367
 
24305
24368
  // src/meta.ts
24306
24369
  var CLI_NAME = "do";
24307
- var VERSION = "1.69.0";
24370
+ var VERSION = "1.71.0";
24308
24371
  var API_PREFIX = "/api/v1";
24309
24372
  var DEFAULT_API_URL = "http://localhost:3001";
24310
24373
 
@@ -24832,14 +24895,18 @@ var COMMAND_SPECS = [
24832
24895
  path: ["capture"],
24833
24896
  summary: "Quick-add a task to the inbox from free text.",
24834
24897
  args: [
24835
- { name: "text", required: true, description: "Task title; may embed #tag and !priority." }
24898
+ {
24899
+ name: "text",
24900
+ required: true,
24901
+ description: "Task title; may embed #tag, ! (star) and ~area."
24902
+ }
24836
24903
  ],
24837
24904
  flags: [],
24838
24905
  scopes: ["tasks:write"],
24839
24906
  returns: "Task",
24840
24907
  grammar: {
24841
24908
  "#tag": "Adds a tag. Repeatable: '#home #urgent'.",
24842
- "!priority": "Sets priority: !high|!medium|!low|!none (aliases: !h/!m/!l/!n). Last one wins."
24909
+ "!": "Stars the task \u2014 the 1\u20132 things that matter (aliases: !star/!s/!flag/!f). Drives Today's focus and the starred filter."
24843
24910
  }
24844
24911
  },
24845
24912
  {
@@ -25430,10 +25497,10 @@ var STATUS_MARK = {
25430
25497
  function renderTask(data, mode) {
25431
25498
  const t = data;
25432
25499
  const mark = STATUS_MARK[t.status ?? ""] ?? "\u2022";
25433
- const prio = t.priority && t.priority !== "none" ? paint(mode, "yellow", `!${t.priority} `) : "";
25500
+ const star = t.starred ? paint(mode, "yellow", "\u2605 ") : "";
25434
25501
  const when2 = t.scheduledAt ?? t.dueAt;
25435
25502
  const date6 = when2 ? paint(mode, "dim", ` (${shortDate(when2)})`) : "";
25436
- return `${mark} ${prio}${t.title ?? "(untitled)"}${date6}
25503
+ return `${mark} ${star}${t.title ?? "(untitled)"}${date6}
25437
25504
  ${paint(mode, "dim", t.id)}`;
25438
25505
  }
25439
25506
  function renderToday(data, mode) {
@@ -25444,8 +25511,8 @@ function renderToday(data, mode) {
25444
25511
  const header = paint(mode, "bold", `Today \xB7 ${result.date} \xB7 ${result.count} item(s)`);
25445
25512
  const lines = result.items.map((item) => {
25446
25513
  const tag = paint(mode, bucketColor(item.bucket), `[${item.bucket}]`);
25447
- const prio = item.priority !== "none" ? ` !${item.priority}` : "";
25448
- return ` ${tag} ${item.title}${prio} ${paint(mode, "dim", item.id)}`;
25514
+ const star = item.starred ? paint(mode, "yellow", " \u2605") : "";
25515
+ return ` ${tag} ${item.title}${star} ${paint(mode, "dim", item.id)}`;
25449
25516
  });
25450
25517
  return [header, ...lines].join(`
25451
25518
  `);
@@ -25571,7 +25638,6 @@ function shortDate(iso) {
25571
25638
 
25572
25639
  // src/today.ts
25573
25640
  var OPEN_STATUSES = new Set(["todo", "in_progress"]);
25574
- var PRIORITY_RANK = { high: 0, medium: 1, low: 2, none: 3 };
25575
25641
  function toDate(value) {
25576
25642
  if (value == null)
25577
25643
  return null;
@@ -25600,7 +25666,7 @@ function selectToday(tasks3, now) {
25600
25666
  id: task.id,
25601
25667
  title: task.title,
25602
25668
  status: task.status,
25603
- priority: task.priority,
25669
+ starred: task.starred ?? false,
25604
25670
  bucket,
25605
25671
  scheduledAt: scheduled ? scheduled.toISOString() : null,
25606
25672
  dueAt: due ? due.toISOString() : null
@@ -25631,9 +25697,9 @@ function compareItems(a, b) {
25631
25697
  const byBucket = BUCKET_RANK[a.bucket] - BUCKET_RANK[b.bucket];
25632
25698
  if (byBucket !== 0)
25633
25699
  return byBucket;
25634
- const byPriority = (PRIORITY_RANK[a.priority] ?? 9) - (PRIORITY_RANK[b.priority] ?? 9);
25635
- if (byPriority !== 0)
25636
- return byPriority;
25700
+ const byStar = Number(b.starred) - Number(a.starred);
25701
+ if (byStar !== 0)
25702
+ return byStar;
25637
25703
  const at = a.scheduledAt ?? a.dueAt ?? "";
25638
25704
  const bt = b.scheduledAt ?? b.dueAt ?? "";
25639
25705
  return at.localeCompare(bt);
@@ -25730,7 +25796,7 @@ var HANDLERS = {
25730
25796
  id,
25731
25797
  title: parsed.title,
25732
25798
  tags: parsed.tags,
25733
- ...parsed.priority ? { priority: parsed.priority } : {},
25799
+ ...parsed.starred ? { starred: parsed.starred } : {},
25734
25800
  ...parsed.area ? { areaName: parsed.area } : {},
25735
25801
  ...parsed.scheduledAt ? { scheduledAt: parsed.scheduledAt, allDay: parsed.allDay } : {}
25736
25802
  });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@robbeverhelst/do",
3
- "version": "1.69.0",
3
+ "version": "1.71.0",
4
4
  "private": false,
5
5
  "description": "do — the agent-drivable CLI over the public /api/v1 surface",
6
6
  "type": "module",