# runShellScript JavaScript transformer Symlinks

**URL:** <https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832>\
**Category:** Configuration Help & General Discussion\
**Created:** [January 12, 2023, 5:47pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832 "2023-01-12T17:47:45Z")\
**Posts on this page:** 16\
**Page:** 1

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 5:47pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/1 "2023-01-12T17:47:45Z")

</div>

Hey! I am having some issues with the runShellScript.

I figured out to run command from my computer, I need the full path. so `node` is `/usr/local/bin/node` - I got that by running `which node` in the cli.

For another command, `npx`, get `/usr/local/bin/npx` but thats a symlink to `/usr/local/lib/node_modules/npm/bin/npx-cli.js`

You can get this full path with **readlink -f `which npx`**

But then I get more errors:

```auto
env: node: No such file or directory

```

But if I run the command in my shell, it works.

Should this follow symlinks? If not, how do I run commands that installed on my machine?

```plaintext
async (clipboardContentString) => {
  const shellScript = `/usr/local/bin/node --version`;

  const shellScriptWrapper = {
    script: shellScript, // mandatory
    launchPath: `/bin/zsh`,
  };

  const result = await runShellScript(shellScriptWrapper);
  return result;
};

```

---

<div class="post-metadata">

**Author:** ![Andreas\_Hegenberg](https://community.folivora.ai/user_avatar/community.folivora.ai/andreas_hegenberg/32/39221_2.png) [@Andreas\_Hegenberg](https://community.folivora.ai/u/Andreas_Hegenberg)\
**Post date:** [January 12, 2023, 6:02pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/2 "2023-01-12T18:02:36Z")

</div>

easiest just do an

`echo $PATH` in your Terminal, then use the whole path that is returned from there and provide it with PATH= in the environmentVariables property (probably only a small subset is needed though).  
I think for npx you could also just pass PATH=/usr/local/bin/  
On my machine I had to use `PATH=/usr/local/bin/:/Users/andi/.nvm/versions/node/v14.18.1/bin/` because I'm using nvm

```auto
async (clipboardContentString) => {
  const shellScript = `/usr/local/bin/node --version`;
  const yourPATH = `result from echo $PATH prefixed by PATH=`
  const shellScriptWrapper = {
    script: shellScript, // mandatory
    launchPath: `/bin/zsh`,
    environmentVariables: yourPATH
  };

  const result = await runShellScript(shellScriptWrapper);
  return result;
};

```

Then you don't need to use the full paths to your binaries anymore.

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 6:05pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/3 "2023-01-12T18:05:32Z")

</div>

thank you! That did it - I appreciate it. Making a cool paste transformer for TypeScript

---

<div class="post-metadata">

**Author:** ![Andreas\_Hegenberg](https://community.folivora.ai/user_avatar/community.folivora.ai/andreas_hegenberg/32/39221_2.png) [@Andreas\_Hegenberg](https://community.folivora.ai/u/Andreas_Hegenberg)\
**Post date:** [January 12, 2023, 6:06pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/4 "2023-01-12T18:06:49Z")

</div>

Nice! What does it transform?

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 6:08pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/5 "2023-01-12T18:08:22Z")

</div>

I often have TypeScript that I want to paste into the browser console, so It will just take the TS, strip the types and paste as JS

---

<div class="post-metadata">

**Author:** ![Andreas\_Hegenberg](https://community.folivora.ai/user_avatar/community.folivora.ai/andreas_hegenberg/32/39221_2.png) [@Andreas\_Hegenberg](https://community.folivora.ai/u/Andreas_Hegenberg)\
**Post date:** [January 12, 2023, 6:09pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/6 "2023-01-12T18:09:40Z")

</div>

Ah interesting, basically running tsc on your TypeScript before pasting?

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 6:10pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/7 "2023-01-12T18:10:22Z")

</div>

Yep - using SWC because it's much faster and keeps the comments

---

<div class="post-metadata">

**Author:** ![Andreas\_Hegenberg](https://community.folivora.ai/user_avatar/community.folivora.ai/andreas_hegenberg/32/39221_2.png) [@Andreas\_Hegenberg](https://community.folivora.ai/u/Andreas_Hegenberg)\
**Post date:** [January 12, 2023, 6:11pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/8 "2023-01-12T18:11:00Z")

</div>

didn't know about SWC, need to check that out 🙂

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 6:12pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/9 "2023-01-12T18:12:06Z")

</div>

Yeah, Generally people use TSC for type checking, and then SWC or ESBuild to do a much faster strip types during dev mode.

SWC is inside Parcel, ESBuild is inside Vite

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 6:55pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/10 "2023-01-12T18:55:21Z")

</div>

@Andreas_Hegenberg what is the best way to pass the clipboardContentString to a CLI? just via the command? Env? I thought it would be piped in via stdin - but I was wrong

---

<div class="post-metadata">

**Author:** ![Andreas\_Hegenberg](https://community.folivora.ai/user_avatar/community.folivora.ai/andreas_hegenberg/32/39221_2.png) [@Andreas\_Hegenberg](https://community.folivora.ai/u/Andreas_Hegenberg)\
**Post date:** [January 12, 2023, 7:18pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/11 "2023-01-12T19:18:32Z")

</div>

Ha good point. The escaping could be problematic.

Maybe something like

```auto
const toTransform = btoa(clipboardContentString);
const shellScript = `echo '${toTransform}' | base64 --decode | npx swc -f "test.ts"`

```

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 7:28pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/12 "2023-01-12T19:28:51Z")

</div>

thanks - ended up being able to use this function:

```plaintext
  function encode(str) {
    return encodeURIComponent(str).replace(/[!'()*]/g, (c) => `%${c.charCodeAt(0).toString(16)}`);
  }

```

---

<div class="post-metadata">

**Author:** ![Andreas\_Hegenberg](https://community.folivora.ai/user_avatar/community.folivora.ai/andreas_hegenberg/32/39221_2.png) [@Andreas\_Hegenberg](https://community.folivora.ai/u/Andreas_Hegenberg)\
**Post date:** [January 12, 2023, 7:31pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/13 "2023-01-12T19:31:44Z")

</div>

👍  
I always fall back to base64 if I don't want to think about all the possible ways a unescaped string can break stuff 😅

Btw. if you are using this with the "Transform & Replace Selection With Java Script" action - I just found a bug that can crash BTT, at least on Ventura. Will upload a fixed alpha in a few minutes.

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 7:37pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/14 "2023-01-12T19:37:03Z")

</div>

Hahah you are too fast - I just came back here to say it's crashing when I try it use from the clipboard manager.

---

<div class="post-metadata">

**Author:** ![Andreas\_Hegenberg](https://community.folivora.ai/user_avatar/community.folivora.ai/andreas_hegenberg/32/39221_2.png) [@Andreas\_Hegenberg](https://community.folivora.ai/u/Andreas_Hegenberg)\
**Post date:** [January 12, 2023, 7:44pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/15 "2023-01-12T19:44:37Z")

</div>

It seems to work fine here now with 3.9991 (get via "Check For Alpha Version Updates", I only tested the base64 variant )

---

<div class="post-metadata">

**Author:** ![wesbos](https://community.folivora.ai/user_avatar/community.folivora.ai/wesbos/32/24194_2.png) [@wesbos](https://community.folivora.ai/u/wesbos)\
**Post date:** [January 12, 2023, 8:18pm UTC](https://community.folivora.ai/t/runshellscript-javascript-transformer-symlinks/29832/16 "2023-01-12T20:18:16Z")

</div>

It works! Thanks a ton! [GitHub - wesbos/clipboard-ts](https://github.com/wesbos/clipboard-ts)
