prettier-plugin-hug-call-arguments 0.1.6 → 0.1.8

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.
package/README.md CHANGED
@@ -120,8 +120,8 @@ db.updateTable("User").set({
120
120
  ## How it works
121
121
 
122
122
  This plugin wraps Prettier's built-in `estree` printer and only overrides the
123
- `print` step for `CallExpression` nodes that match one of two narrow, specific
124
- shapes.
123
+ `print` step for `CallExpression` and `ArrowFunctionExpression` nodes that
124
+ match one of a few narrow, specific shapes.
125
125
 
126
126
  **Hugging a call-wrapped callback:**
127
127
 
@@ -141,6 +141,31 @@ shapes.
141
141
  - there's no blank line between arguments, no comments on the relevant
142
142
  nodes, and no TS type arguments
143
143
 
144
+ **Hugging an arrow function's concise body:**
145
+
146
+ ```js
147
+ // input
148
+ const f = (data) =>
149
+ pgBoss.then((boss) => {
150
+ return boss.send(jobName, data);
151
+ });
152
+
153
+ // with this plugin
154
+ const f = (data) => pgBoss.then((boss) => {
155
+ return boss.send(jobName, data);
156
+ });
157
+ ```
158
+
159
+ - the arrow has a concise (non-block) body, no type parameters, return type,
160
+ or predicate, and default `arrowParens`
161
+ - the body is a `CallExpression` that needs multi-line printing (Prettier
162
+ already hugs directly after `=>` for other body types — objects, arrays,
163
+ JSX, template literals — so there's no gap to fix there)
164
+ - the resulting line fits `printWidth`; otherwise this falls back to
165
+ Prettier's default (a hardline after `=>`, body indented on its own line).
166
+ The arrow's own parameter list can still break onto its own line first the
167
+ normal way — only the `=> body` boundary is affected
168
+
144
169
  **Flattening a method chain:**
145
170
 
146
171
  - every link is a plain, non-optional `.name(...)` or `[expr](...)` call down
package/dist/index.d.ts CHANGED
@@ -24,6 +24,10 @@ interface ESNode {
24
24
  name?: string;
25
25
  arguments?: ESNode[];
26
26
  body?: ESNode;
27
+ params?: ESNode[];
28
+ async?: boolean;
29
+ returnType?: unknown;
30
+ predicate?: unknown;
27
31
  }
28
32
  declare const plugin: Plugin<ESNode>;
29
33
  export = plugin;
package/dist/index.js CHANGED
@@ -269,6 +269,62 @@ function tryHugWrappedCallback(path, options, print) {
269
269
  }
270
270
  return [breakParent, primaryDoc];
271
271
  }
272
+ /**
273
+ * Handles an arrow function with a concise (non-block) body that's itself a
274
+ * call needing multi-line printing, e.g.:
275
+ *
276
+ * const f = (data: Job) => pgBoss.then((boss) => {
277
+ * ...
278
+ * });
279
+ *
280
+ * Prettier hugs a concise body directly after `=>` for several node types
281
+ * (object/array literals, JSX, template literals, ...) but not for a plain
282
+ * `CallExpression` — it always inserts a hardline after `=>` and indents the
283
+ * call onto its own line instead, even when the call's own last argument is
284
+ * already going to hug and break internally regardless. This reproduces
285
+ * Prettier's own arrow-head printing for the narrow, common shape (no type
286
+ * parameters, return type, or predicate; default `arrowParens`) and keeps
287
+ * the body on the same line as `=>` instead.
288
+ */
289
+ function tryHugArrowBody(path, options, print) {
290
+ const { node } = path;
291
+ if (node.type !== "ArrowFunctionExpression" ||
292
+ hasComment(node) ||
293
+ node.typeParameters ||
294
+ node.returnType ||
295
+ node.predicate ||
296
+ options.arrowParens === "avoid") {
297
+ return undefined;
298
+ }
299
+ const body = node.body;
300
+ if (!body || body.type !== "CallExpression" || hasComment(body)) {
301
+ return undefined;
302
+ }
303
+ const bodyDoc = print("body");
304
+ if (!wouldBreakStandalone(bodyDoc, options)) {
305
+ return undefined;
306
+ }
307
+ const trailingComma = options.trailingComma === "all" ? "," : "";
308
+ const paramsDoc = group([
309
+ "(",
310
+ indent([softline, join([",", line], path.map(print, "params"))]),
311
+ ifBreak(trailingComma),
312
+ softline,
313
+ ")",
314
+ ]);
315
+ const primaryDoc = [
316
+ node.async ? "async " : "",
317
+ paramsDoc,
318
+ " => ",
319
+ bodyDoc,
320
+ ];
321
+ // Same column-0 blind spot as `tryHugWrappedCallback` (see its comment) —
322
+ // conservative, but errs toward Prettier's own default when unsure.
323
+ if (!fitsWhenFlattened(primaryDoc, options)) {
324
+ return undefined;
325
+ }
326
+ return [breakParent, primaryDoc];
327
+ }
272
328
  const MAX_CHAIN_LINKS = 6;
273
329
  /**
274
330
  * Builds the `(...)` doc for one link's argument list the same way a plain,
@@ -403,6 +459,7 @@ const plugin = {
403
459
  ...estreePrinter,
404
460
  print(path, options, print, args) {
405
461
  const hugged = tryHugWrappedCallback(path, options, print) ??
462
+ tryHugArrowBody(path, options, print) ??
406
463
  tryHugChainArgument(path, options, print);
407
464
  return hugged === undefined
408
465
  ? estreePrinter.print(path, options, print, args)
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "prettier-plugin-hug-call-arguments",
3
- "version": "0.1.6",
3
+ "version": "0.1.8",
4
4
  "description": "Prettier plugin: hug the last call argument even when it's wrapped in another call, e.g. app.delete(\"/x\", catchAsync(async (req, res) => { ... })). Fixes https://github.com/prettier/prettier/issues/11080",
5
5
  "author": "soso tsertsvadze",
6
6
  "license": "MIT",