From da73d7f07631de814c5fc1d9de4605b74b7dfcb5 Mon Sep 17 00:00:00 2001 From: Ben Lovy Date: Tue, 19 Nov 2024 15:56:24 -0500 Subject: [PATCH 1/4] add test --- packages/server/src/package/check/tests.rs | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/packages/server/src/package/check/tests.rs b/packages/server/src/package/check/tests.rs index 10f46f434..a913c1283 100644 --- a/packages/server/src/package/check/tests.rs +++ b/packages/server/src/package/check/tests.rs @@ -70,6 +70,26 @@ async fn nonexistent_function() -> tg::Result<()> { .await } +#[tokio::test] +async fn no_return_value() -> tg::Result<()> { + test( + temp::directory! { + "tangram.ts" => indoc!(r" + export default tg.target(() => {}); + "), + }, + |_, output| async move { + assert_json_snapshot!(output, @r#" + { + "diagnostics": [] + } + "#); + Ok(()) + }, + ) + .await +} + async fn test(artifact: temp::Artifact, assertions: F) -> tg::Result<()> where F: FnOnce(Server, tg::package::check::Output) -> Fut, From 05697aa593aeac7298c5fc3dcca4d10488853ff5 Mon Sep 17 00:00:00 2001 From: David Yamnitsky Date: Mon, 25 Nov 2024 15:51:18 -0500 Subject: [PATCH 2/4] impl --- biome.json | 1 + packages/runtime/src/resolve.ts | 6 ++++-- packages/runtime/src/target.ts | 14 +++++++------- packages/runtime/tangram.d.ts | 14 ++++++++------ 4 files changed, 20 insertions(+), 15 deletions(-) diff --git a/biome.json b/biome.json index dadb42fa7..0dca84ebc 100644 --- a/biome.json +++ b/biome.json @@ -20,6 +20,7 @@ "useConst": "off" }, "suspicious": { + "noConfusingVoidType": "off", "noExplicitAny": "off", "noRedeclare": "off", "useIsArray": "off" diff --git a/packages/runtime/src/resolve.ts b/packages/runtime/src/resolve.ts index 542cd2646..47d31892c 100644 --- a/packages/runtime/src/resolve.ts +++ b/packages/runtime/src/resolve.ts @@ -2,8 +2,9 @@ import * as im from "immutable"; import * as tg from "./index.ts"; import type { MaybePromise } from "./util.ts"; -export type Unresolved = MaybePromise< +export type Unresolved = MaybePromise< T extends + | void | undefined | boolean | number @@ -20,7 +21,8 @@ export type Unresolved = MaybePromise< : never >; -export type Resolved> = T extends +export type Resolved> = T extends + | void | undefined | boolean | number diff --git a/packages/runtime/src/target.ts b/packages/runtime/src/target.ts index 8d41f2307..3fec2a22e 100644 --- a/packages/runtime/src/target.ts +++ b/packages/runtime/src/target.ts @@ -14,7 +14,7 @@ export let setCurrentTarget = (target: Target) => { type FunctionArg< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, > = { function: (...args: A) => tg.Unresolved; module: tg.Module; @@ -23,15 +23,15 @@ type FunctionArg< export function target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, >(arg: FunctionArg): Target; export function target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, >(...args: tg.Args): Promise>; export function target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, >( ...args: [FunctionArg] | tg.Args ): MaybePromise> { @@ -70,7 +70,7 @@ export function target< export interface Target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, > extends globalThis.Function { (...args: { [K in keyof A]: tg.Unresolved }): Promise; } @@ -78,7 +78,7 @@ export interface Target< // biome-ignore lint/suspicious/noUnsafeDeclarationMerging: This is necessary to make targets callable. export class Target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, > extends globalThis.Function { #state: Target.State; #f: Function | undefined; @@ -116,7 +116,7 @@ export class Target< static async new< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, >(...args: tg.Args): Promise> { let arg = await Target.arg(...args); let args_ = arg.args ?? []; diff --git a/packages/runtime/tangram.d.ts b/packages/runtime/tangram.d.ts index 9704c3631..5ad6a0782 100644 --- a/packages/runtime/tangram.d.ts +++ b/packages/runtime/tangram.d.ts @@ -546,17 +546,17 @@ declare namespace tg { /** Create a target. */ export function target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, >(function_: (...args: A) => tg.Unresolved): tg.Target; export function target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, >(...args: tg.Args): Promise>; /** A target. */ export interface Target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, > { /** Build this target. */ // biome-ignore lint/style/useShorthandFunctionType: interface is necessary . @@ -566,7 +566,7 @@ declare namespace tg { /** A target. */ export class Target< A extends Array = Array, - R extends tg.Value = tg.Value, + R extends void | tg.Value = void | tg.Value, > extends globalThis.Function { /** Get a target with an ID. */ static withId(id: tg.Target.Id): tg.Target; @@ -940,8 +940,9 @@ declare namespace tg { * Unresolved> = MaybePromise }>>> * ``` */ - export type Unresolved = tg.MaybePromise< + export type Unresolved = tg.MaybePromise< T extends + | void | undefined | boolean | number @@ -970,7 +971,8 @@ declare namespace tg { * Resolved>>> = Array * ``` */ - export type Resolved> = T extends + export type Resolved> = T extends + | void | undefined | boolean | number From ce5bb371d1554eabb549f203b9f19ef4aea7c714 Mon Sep 17 00:00:00 2001 From: David Yamnitsky Date: Mon, 25 Nov 2024 16:35:51 -0500 Subject: [PATCH 3/4] remove void from resolved and unresolved --- packages/runtime/src/resolve.ts | 8 +++----- packages/runtime/src/target.ts | 6 +++++- packages/runtime/tangram.d.ts | 14 +++++++++----- 3 files changed, 17 insertions(+), 11 deletions(-) diff --git a/packages/runtime/src/resolve.ts b/packages/runtime/src/resolve.ts index 47d31892c..6ac94e725 100644 --- a/packages/runtime/src/resolve.ts +++ b/packages/runtime/src/resolve.ts @@ -1,10 +1,9 @@ -import * as im from "immutable"; +import im from "immutable"; import * as tg from "./index.ts"; import type { MaybePromise } from "./util.ts"; -export type Unresolved = MaybePromise< +export type Unresolved = MaybePromise< T extends - | void | undefined | boolean | number @@ -21,8 +20,7 @@ export type Unresolved = MaybePromise< : never >; -export type Resolved> = T extends - | void +export type Resolved> = T extends | undefined | boolean | number diff --git a/packages/runtime/src/target.ts b/packages/runtime/src/target.ts index 3fec2a22e..197b0d1ae 100644 --- a/packages/runtime/src/target.ts +++ b/packages/runtime/src/target.ts @@ -16,7 +16,11 @@ type FunctionArg< A extends Array = Array, R extends void | tg.Value = void | tg.Value, > = { - function: (...args: A) => tg.Unresolved; + function: ( + ...args: A + ) => R extends void + ? MaybePromise + : tg.Unresolved>; module: tg.Module; name: string; }; diff --git a/packages/runtime/tangram.d.ts b/packages/runtime/tangram.d.ts index 5ad6a0782..0cb5936e4 100644 --- a/packages/runtime/tangram.d.ts +++ b/packages/runtime/tangram.d.ts @@ -547,7 +547,13 @@ declare namespace tg { export function target< A extends Array = Array, R extends void | tg.Value = void | tg.Value, - >(function_: (...args: A) => tg.Unresolved): tg.Target; + >( + function_: ( + ...args: A + ) => R extends void + ? MaybePromise + : tg.Unresolved>, + ): tg.Target; export function target< A extends Array = Array, R extends void | tg.Value = void | tg.Value, @@ -940,9 +946,8 @@ declare namespace tg { * Unresolved> = MaybePromise }>>> * ``` */ - export type Unresolved = tg.MaybePromise< + export type Unresolved = tg.MaybePromise< T extends - | void | undefined | boolean | number @@ -971,8 +976,7 @@ declare namespace tg { * Resolved>>> = Array * ``` */ - export type Resolved> = T extends - | void + export type Resolved> = T extends | undefined | boolean | number From e50919714a204ccb9e4538287a73f0b26a62c3bf Mon Sep 17 00:00:00 2001 From: David Yamnitsky Date: Mon, 25 Nov 2024 20:44:22 -0500 Subject: [PATCH 4/4] fix boolean case --- packages/runtime/src/resolve.ts | 38 +++++++++++++++------------ packages/runtime/src/target.ts | 5 ++-- packages/runtime/tangram.d.ts | 46 +++++++++++++++++++-------------- 3 files changed, 50 insertions(+), 39 deletions(-) diff --git a/packages/runtime/src/resolve.ts b/packages/runtime/src/resolve.ts index 6ac94e725..a036cdd55 100644 --- a/packages/runtime/src/resolve.ts +++ b/packages/runtime/src/resolve.ts @@ -2,23 +2,27 @@ import im from "immutable"; import * as tg from "./index.ts"; import type { MaybePromise } from "./util.ts"; -export type Unresolved = MaybePromise< - T extends - | undefined - | boolean - | number - | string - | tg.Object - | Uint8Array - | tg.Mutation - | tg.Template - ? T - : T extends Array - ? Array> - : T extends { [key: string]: tg.Value } - ? { [K in keyof T]: Unresolved } - : never ->; +export type Unresolved = MaybePromise>; + +export type UnresolvedInner = T extends + | undefined + | boolean + | number + | string + | tg.Object + | Uint8Array + | tg.Mutation + | tg.Template + ? T + : T extends Array + ? Array> + : T extends { + [key: string]: tg.Value; + } + ? { + [K in keyof T]: Unresolved; + } + : never; export type Resolved> = T extends | undefined diff --git a/packages/runtime/src/target.ts b/packages/runtime/src/target.ts index 197b0d1ae..5ffc3a755 100644 --- a/packages/runtime/src/target.ts +++ b/packages/runtime/src/target.ts @@ -1,4 +1,5 @@ import * as tg from "./index.ts"; +import type { UnresolvedInner } from "./resolve.ts"; import { type MaybeMutationMap, type MaybeNestedArray, @@ -18,9 +19,7 @@ type FunctionArg< > = { function: ( ...args: A - ) => R extends void - ? MaybePromise - : tg.Unresolved>; + ) => MaybePromise>>; module: tg.Module; name: string; }; diff --git a/packages/runtime/tangram.d.ts b/packages/runtime/tangram.d.ts index 0cb5936e4..d541c321a 100644 --- a/packages/runtime/tangram.d.ts +++ b/packages/runtime/tangram.d.ts @@ -408,7 +408,9 @@ declare namespace tg { } /** Create a symlink. */ - export let symlink: (arg: tg.Unresolved) => Promise; + export let symlink: ( + arg: tg.Unresolved, + ) => Promise; /** A symlink. */ export class Symlink { @@ -550,9 +552,9 @@ declare namespace tg { >( function_: ( ...args: A - ) => R extends void - ? MaybePromise - : tg.Unresolved>, + ) => MaybePromise< + R extends void ? void : tg.UnresolvedInner> + >, ): tg.Target; export function target< A extends Array = Array, @@ -947,23 +949,29 @@ declare namespace tg { * ``` */ export type Unresolved = tg.MaybePromise< - T extends - | undefined - | boolean - | number - | string - | tg.Object - | Uint8Array - | tg.Mutation - | tg.Template - ? T - : T extends Array - ? Array> - : T extends { [key: string]: tg.Value } - ? { [K in keyof T]: tg.Unresolved } - : never + tg.UnresolvedInner >; + type UnresolvedInner = T extends + | undefined + | boolean + | number + | string + | tg.Object + | Uint8Array + | tg.Mutation + | tg.Template + ? T + : T extends Array + ? Array> + : T extends { + [key: string]: tg.Value; + } + ? { + [K in keyof T]: Unresolved; + } + : never; + /** * This computed type performs the inverse of `Unresolved`. It takes a type and returns the output of calling `resolve` on a value of that type. Here are some examples: *