Skip to content

bug: Parse error when using typed template function #329

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
1 of 2 tasks
SimonSimCity opened this issue Apr 9, 2025 · 0 comments · May be fixed by #332
Open
1 of 2 tasks

bug: Parse error when using typed template function #329

SimonSimCity opened this issue Apr 9, 2025 · 0 comments · May be fixed by #332
Labels

Comments

@SimonSimCity
Copy link

SimonSimCity commented Apr 9, 2025

Did you check existing issues?

  • I have read all the tree-sitter docs if it relates to using the parser
  • I have searched the existing issues of tree-sitter-typescript

Tree-Sitter CLI Version, if relevant (output of tree-sitter --version)

No response

Describe the bug

I see a parsing error in my editor (zed), but can't say much more than that. It seems that the problem is a result of the typed template function, but any line I change or remove seems to have an influence on the outcome.

Steps To Reproduce/Bad Parse Tree

export class TRPCError extends Error {
  constructor(opts: { message?: string; code: string }) {
    super(opts.code);
  }
}
let sql: <T = unknown>(
  sqlFragments: TemplateStringsArray,
  ...parameters: unknown[]
) => T[];
const fn = (...args: unknown[]) => args;

export default {
  abc: () => {
    fn(() => [fn(sql<never[]>`'[]'`)]);
  },
  cde: fn(async ({ ctx, input }) => {
    new TRPCError({
      code: "NOT_FOUND",
      message: `The company was not found.`,
    });

    await Promise.resolve(fn([fn([{}]), fn((oc: unknown) => oc)]));
  }),
};

export const foo = `No id found.`;

Try to parse this code. Remove the line message: ``The company was not found.``, and try again. The result, I guess, should be almost the same as when having the line in place 😊

Expected Behavior/Parse Tree

Should return the same as with the deleted line, I guess.

Repro

export class TRPCError extends Error {
  constructor(opts: { message?: string; code: string }) {
    super(opts.code);
  }
}
let sql: <T = unknown>(
  sqlFragments: TemplateStringsArray,
  ...parameters: unknown[]
) => T[];
const fn = (...args: unknown[]) => args;

export default {
  abc: () => {
    fn(() => [fn(sql<never[]>`'[]'`)]);
  },
  cde: fn(async ({ ctx, input }) => {
    new TRPCError({
      code: "NOT_FOUND",
    });

    await Promise.resolve(fn([fn([{}]), fn((oc: unknown) => oc)]));
  }),
};

export const foo = `No id found.`;
rusiaaman added a commit to rusiaaman/tree-sitter-typescript that referenced this issue Jun 2, 2025
Fixes tree-sitter#329

The issue was that template call expressions only allowed primary_expression
or new_expression as the function, but instantiation expressions like
`sql<Type[]>`template`` were not supported.

This change adds $.instantiation_expression to the allowed function types
for template calls, enabling proper parsing of patterns like:
- sql<never[]>`'[]'`
- tag<string>`Hello ${name}`
- func<Type[]>`SELECT * FROM table`

Testing shows this resolves the parsing inconsistency where removing
certain lines would cause the entire file to fail parsing.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant