Closed KeqiZeng closed 3 years ago
There are also some informations maybe can be helpful.
which brew
/opt/homebrew/bin/brew
which blueutil
/opt/homebrew/bin/blueutil
I cannot reproduce because I have no M1 mac handy. But it seems PATH does not know /opt/homebrew/bin
.
The easiest way is to open con_manager.py
script and add full path to os.popen
:
os.popen(f'blueutil --connect {adr}')
→ os.popen(f'/opt/homebrew/bin/blueutil --connect {adr}')
and
os.popen(f'blueutil --disconnect {adr}')
→ os.popen(f'/opt/homebrew/bin/blueutil --disconnect {adr}')
Hi, I have tried just now and got the same issue. Here is my con_manager.py
#!/opt/homebrew/bin/python3
import os
from Alfred3 import Tools
# automatic blueutil installer
os.environ['PATH'] = os.popen('./_sharedresources "blueutil"').readline()
query = Tools.getArgv(1)
adr, switch = tuple(query.split(";"))
if switch == "disconnected":
Tools.log(adr)
os.popen(f'/opt/homebrew/bin/blueutil --connect {adr}')
else:
os.popen(f'/opt/homebrew/bin/blueutil --disconnect {adr}')
And I think /opt/homebrew/bin
is already in my PATH
echo $PATH
/opt/homebrew/bin:/opt/homebrew/sbin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/go/bin:/Applications/Wireshark.app/Contents/MacOS:/Users/ketch/go/bin:/opt/homebrew/opt/llvm/bin
Ok, sure....you get the same error because it seems to fail before within py3.sh
Can you open first script action and change it to:
Language: External Script
and point to airp.py
Sorry bro, I come again... I have changed the first script as you said but it can't also work well. I tried running /usr/bin/python3 airp.py
in my terminal and got
{
"items": [
{
"title": "Ketch's AirPods",
"subtitle": "Ketch's AirPods are connected, Press \u23ce to disconnect...",
"arg": "b8-81-fa-76-f8-32;connected",
"uid": "b8-81-fa-76-f8-32",
"icon": {
"type": "image",
"path": "airpod2.png"
}
}
]
}%
or
{
"items": [
{
"title": "Ketch's AirPods",
"subtitle": "Ketch's AirPods are NOT connected, \u23ce to connect...",
"arg": "b8-81-fa-76-f8-32;disconnected",
"uid": "b8-81-fa-76-f8-32",
"icon": {
"type": "image",
"path": "airpod2_case.png"
}
}
]
}%
I think it can work so well until now, blueutil
can be found. Maybe we have solved some problems .But in alfred it seems like blueutil
can't also be found just like at the beginning.
[17:06:20.010] Logging Started...
[17:06:23.062] AirPods Connector[Script Filter] Queuing argument '(null)'
[17:06:23.884] AirPods Connector[Script Filter] Script with argv '(null)' finished
[17:06:23.887] STDERR: AirPods Connector[Script Filter] tar: Error opening archive: Unrecognized archive format
Could not download blueutil.
/bin/sh: blueutil: No such file or directory
[17:06:23.888] AirPods Connector[Script Filter] {
"items": [
{
"title": "BLUEUTIL required!",
"subtitle": "Please install with \"brew install blueutil\" first",
"valid": false
}
]
}
Here is my airp.py
, I think I did not change it.
#!/usr/bin/python3
import json
import os
import plistlib
import sys
from Alfred3 import Items, Tools
AIRPD_PRODUCT_INDX = {
8202: "airpodmax",
8206: "airpodpro",
8194: "airpod1",
8207: "airpod2",
8203: "powerbeatspro"
}
# automatic blueutil installer
os.environ['PATH'] = os.popen('./_sharedresources "blueutil"').readline()
def airpod_info(device_id: str) -> tuple:
"""
Get airpod info with a given address (MAC)
Args:
device_id (str): MAC address of the AirPod to search
Returns:
tuble: productlabel, productid, vendorid
"""
with open("/Library/Preferences/com.apple.Bluetooth.plist", "rb") as f:
pl = plistlib.load(f)
devices: dict = pl.get("DeviceCache")
ret: tuple = tuple()
for d, v in devices.items():
if device_id in d:
product_id: str = v.get("ProductID")
product_label: str = AIRPD_PRODUCT_INDX.get(product_id)
vendor_id: str = v.get("VendorID")
ret: tuple = (product_label, product_id, vendor_id)
break
return ret
def paired_airpods() -> dict:
"""
Get paired AirPods including info
Returns:
dict: dict with paired AirPod name including dict with info
"""
jsn: dict = json.loads(os.popen('blueutil --paired --format json').read())
out_dict = {}
for i in jsn:
address: str = i.get('address')
prod_label, prod_id, vendor_id = airpod_info(address)
if vendor_id == 76 and prod_id in AIRPD_PRODUCT_INDX.keys():
out_dict.update(
{i.get('name'):
{"address": i.get('address'),
"connected": i.get('connected'),
"prod_label": prod_label
}
}
)
return out_dict
def is_blueutil() -> bool:
"""
Checks if Blueutil was properly installed
Returns:
bool: True=available, False=not found
"""
blueutil: str = os.popen("blueutil -v").readline()
if blueutil == "":
return False
else:
return True
def main():
query = Tools.getArgv(1)
wf = Items()
if is_blueutil():
for ap_name, status in paired_airpods().items():
adr: str = status.get('address')
ap_type: str = status.get('prod_label')
is_connected: bool = status.get('connected')
con_str: str = "connected, Press \u23CE to disconnect..." if is_connected else "NOT connected, \u23CE to connect..."
ico: str = f"{ap_type}.png" if is_connected else f"{ap_type}_case.png"
con_switch: str = "connected" if is_connected else "disconnected"
if query == "" or query.lower() in ap_name.lower():
wf.setItem(
title=ap_name,
subtitle=f"{ap_name} are {con_str}",
arg=f"{adr};{con_switch}",
uid=adr
)
wf.setIcon(ico, "image")
wf.addItem()
else:
wf.setItem(
title="BLUEUTIL required!",
subtitle='Please install with "brew install blueutil" first',
valid=False
)
wf.addItem()
wf.write()
if __name__ == "__main__":
main()
and con_manager.py
(I find /usr/bin/python3
can also work)
#!/usr/bin/python3
import os
from Alfred3 import Tools
# automatic blueutil installer
os.environ['PATH'] = os.popen('./_sharedresources "blueutil"').readline()
query = Tools.getArgv(1)
adr, switch = tuple(query.split(";"))
if switch == "disconnected":
Tools.log(adr)
os.popen(f'/opt/homebrew/bin/blueutil --connect {adr}')
else:
os.popen(f'/opt/homebrew/bin/blueutil --disconnect {adr}')
I'm so sorry for wasting your time.
oh forgot to mention to disable automatic blueutil installer. Comment out following line in both scripts:
os.environ['PATH'] = os.popen('./_sharedresources "blueutil"').readline()
Hey, I think I find the problem. I have tested as you said, but it seems nothing changed. Then I change all blueutil
in airp.py to /opt/homebrew/bin/blueutil
and it can work well for me. Before this, airp.py
can actually work well in my terminal but not in alfred. It's so strange.
So, I think for m1 mac, maybe we need to
open first script action and change it to: Language: External Script, and point to airp.py
then change all blueutil
to /opt/homebrew/bin/blueutil
in both scripts.
I hope this is helpful for those who use m1 mac. Finally, thank you again for the nice WF. It's great!
Hey guy, I have tried the WF on my m1 macbook air, but it can not work well. At first, it can't find python3, so I manually changed the path of python3 to
/opt/homebrew/bin/python3
. And it can not also downloadblueutil
automatically, so I runbrew install blueutil
in my terminal. In my terminal i can useblueutil
just likeHowever, it seems like
blueutil
can't be found. I got this from alfredI think this issue comes from m1 chip or path of
blueutil
, but I don't know how to tell the script whereblueutil
is. Any help would be appreciated!!