A temporary fix:
pkill -f /usr/share/cursor/cursor
sleep 2
sudo python3 /tmp/patch_cursor_js.py
python3 /tmp/fix_cursor_model.py
/usr/share/cursor/cursor &
Patch, /tmp/fix_cursor_model.py:
import shutil
import os
from datetime import datetime
JS_PATH = "/usr/share/cursor/resources/app/out/vs/workbench/workbench.desktop.main.js"
BACKUP_SUFFIX = f".bak.{datetime.now().strftime('%Y%m%d_%H%M%S')}"
BACKUP_PATH = JS_PATH + BACKUP_SUFFIX
# Only back up if no backup exists yet today (avoid multiple large backups)
existing = [f for f in os.listdir(os.path.dirname(JS_PATH)) if f.startswith('workbench.desktop.main.js.bak')]
if not existing:
print(f"Backing up -> {BACKUP_PATH}")
shutil.copy2(JS_PATH, BACKUP_PATH)
else:
print(f"Backup already exists: {existing[0]}, skipping")
with open(JS_PATH, 'r', encoding='utf-8', errors='replace') as f:
content = f.read()
patches = []
# Patch 1: getter - intercept reads of claude-opus-4-7 preference and force effort=medium
OLD1 = 'getModelParameterPreferences(e){return this.reactiveStorageService.applicationUserPersistentStorage.aiSettings.modelParameterPreferences?.[e]}'
NEW1 = ('getModelParameterPreferences(e){'
'const _p=this.reactiveStorageService.applicationUserPersistentStorage.aiSettings.modelParameterPreferences?.[e];'
'return e==="claude-opus-4-7"&&_p?{..._p,parameters:_p.parameters.map(p=>p.id==="effort"&&p.value==="xhigh"?{...p,value:"medium"}:p)}:_p;'
'}')
patches.append(('getter', OLD1, NEW1))
# Patch 2: default variant writer - already applied, verify it's still there
OLD2 = 'yk(()=>{this._reactiveStorageService.setApplicationUserPersistentStorage("availableDefaultModels2",o),'
if OLD2 not in content:
# Patch was already applied from previous run, use the patched version as OLD
OLD2_PATCHED = ('o=o.map(function(m){if(m.name==="claude-opus-4-7"){return Object.assign({},m,{variants:m.variants.map(function(v){if(v.isDefaultNonMaxConfig||v.isDefaultMaxConfig){return Object.assign({},v,{parameterValues:v.parameterValues.map(function(p){return p.id==="effort"?Object.assign({},p,{value:"medium"}):p;})});}return v;})});}return m;});'
'yk(()=>{this._reactiveStorageService.setApplicationUserPersistentStorage("availableDefaultModels2",o),')
if OLD2_PATCHED in content:
print("Patch 2 (default variant writer) already applied, skipping")
patches.append(('default-variant-writer', None, None))
else:
print("WARNING: Could not find patch 2 target (old or patched form)")
patches.append(('default-variant-writer', None, None))
else:
NEW2 = ('o=o.map(function(m){if(m.name==="claude-opus-4-7"){return Object.assign({},m,{variants:m.variants.map(function(v){if(v.isDefaultNonMaxConfig||v.isDefaultMaxConfig){return Object.assign({},v,{parameterValues:v.parameterValues.map(function(p){return p.id==="effort"?Object.assign({},p,{value:"medium"}):p;})});}return v;})});}return m;});'
'yk(()=>{this._reactiveStorageService.setApplicationUserPersistentStorage("availableDefaultModels2",o),')
patches.append(('default-variant-writer', OLD2, NEW2))
for name, old, new in patches:
if old is None:
continue
count = content.count(old)
if count == 0:
print(f"SKIP {name}: target not found")
continue
if count > 1:
print(f"WARNING {name}: {count} occurrences found, replacing all")
content = content.replace(old, new)
print(f"OK {name}: replaced {count} occurrence(s)")
with open(JS_PATH, 'w', encoding='utf-8', errors='replace') as f:
f.write(content)
print("Done. Restart Cursor to apply.")