diff --git a/roles/vhosts/qmd/tasks/main.yml b/roles/vhosts/qmd/tasks/main.yml index 59e95d1..22e9135 100644 --- a/roles/vhosts/qmd/tasks/main.yml +++ b/roles/vhosts/qmd/tasks/main.yml @@ -126,6 +126,13 @@ ansible.builtin.command: cmd: npm install chdir: "{{ qmd_source_dir }}" + # Pin Homebrew node@24 ahead of any nvm/other node on Darwin so the native + # better-sqlite3 module is compiled against the same Node ABI that the + # launchd service and `qmd status` run with. Otherwise a host with nvm node + # first builds the module for the wrong NODE_MODULE_VERSION and qmd aborts + # with ERR_DLOPEN_FAILED. Linux PATH is left untouched. + environment: + PATH: "{{ '/opt/homebrew/bin:/usr/local/bin:' if ansible_os_family == 'Darwin' else '' }}{{ ansible_env.PATH }}" become: true become_user: "{{ qmd_user }}" when: @@ -136,6 +143,8 @@ ansible.builtin.command: cmd: npm run build chdir: "{{ qmd_source_dir }}" + environment: + PATH: "{{ '/opt/homebrew/bin:/usr/local/bin:' if ansible_os_family == 'Darwin' else '' }}{{ ansible_env.PATH }}" become: true become_user: "{{ qmd_user }}" when: @@ -296,7 +305,11 @@ - name: Validate QMD status ansible.builtin.command: cmd: "{{ qmd_binary_path }} status" + # qmd's /bin/sh wrapper invokes `node`; on Darwin pin Homebrew node@24 first + # so it matches the ABI better-sqlite3 was built with (see npm tasks above), + # instead of falling through to an nvm node and failing ERR_DLOPEN_FAILED. environment: + PATH: "{{ '/opt/homebrew/bin:/usr/local/bin:' if ansible_os_family == 'Darwin' else '' }}{{ ansible_env.PATH }}" HOME: "{{ qmd_home }}" QMD_EMBED_API_BASE_URL: "{{ qmd_embed_api_base_url }}" QMD_EMBED_MODEL: "{{ qmd_embed_model }}"