[{"data":1,"prerenderedAt":1254},["ShallowReactive",2],{"doc:\u002Fpyqgis-fundamentals-environment-setup\u002Fqgis-python-console-basics\u002Fhow-to-install-qgis-python-bindings-on-windows":3},{"id":4,"title":5,"body":6,"description":1243,"extension":1244,"meta":1245,"navigation":484,"path":1250,"seo":1251,"stem":1252,"__hash__":1253},"docs\u002Fpyqgis-fundamentals-environment-setup\u002Fqgis-python-console-basics\u002Fhow-to-install-qgis-python-bindings-on-windows\u002Findex.md","How to Install QGIS Python Bindings on Windows",{"type":7,"value":8,"toc":1229},"minimark",[9,13,38,60,258,263,266,332,336,339,413,418,421,437,448,636,644,648,655,670,712,735,739,742,833,837,840,945,949,952,997,1005,1009,1085,1089,1104,1108,1121,1130,1140,1158,1172,1176,1225],[10,11,5],"h1",{"id":12},"how-to-install-qgis-python-bindings-on-windows",[14,15,16,17,21,22,26,27,30,31,37],"p",{},"The fastest and officially supported way to install QGIS Python bindings on Windows is the ",[18,19,20],"strong",{},"OSGeo4W Network Installer",". It resolves the compiled C++ dependencies, registers the environment variables PyQGIS needs, and links ",[23,24,25],"code",{},"qgis.core"," and ",[23,28,29],{},"qgis.gui"," to a managed Python runtime. ",[18,32,33,34],{},"Do not run ",[23,35,36],{},"pip install pyqgis"," — the PyPI package is a documentation stub with none of the Windows binaries the real bindings require.",[14,39,40,41,46,47,50,51,54,55,59],{},"This is the Windows companion to the interactive workflow covered in the parent ",[42,43,45],"a",{"href":44},"\u002Fpyqgis-fundamentals-environment-setup\u002Fqgis-python-console-basics\u002F","QGIS Python Console Basics"," guide. Inside QGIS the console already injects the correct ",[23,48,49],{},"PYTHONPATH"," for you; the goal here is to make the same ",[23,52,53],{},"qgis"," modules importable from an ",[56,57,58],"em",{},"external"," interpreter so you can run scripts, IDEs, and automation outside the desktop. If you only want to script from within QGIS, you already have the bindings and can skip to the console guide.",[61,62,67,71,75,82,91,101,108,112,119,126,129,135,138,141,147,152,157,161,165,169,174,179,184,189,193,196,200,203,206,209,213,216,219,222,225,232,239,244],"svg",{"viewBox":63,"role":64,"ariaLabel":65,"xmlns":66},"0 0 760 410","img","Decision flow for installing PyQGIS bindings on Windows: if you only script inside QGIS nothing is needed, otherwise choose the OSGeo4W Network Installer or the Standalone Installer, both ending at a verified import of qgis.core","http:\u002F\u002Fwww.w3.org\u002F2000\u002Fsvg",[68,69,70],"title",{},"Choosing a Windows PyQGIS install path",[72,73,74],"desc",{},"Start by asking whether you need PyQGIS to run outside QGIS Desktop. If no, the built-in Python Console already loads the bindings and nothing is installed. If yes, take Method 1, the OSGeo4W Network Installer, which auto-registers QGIS_PREFIX_PATH, PYTHONPATH and PATH, or Method 2, the Standalone Installer, where you set the paths yourself through a run_pyqgis.bat launcher. Both methods converge on a working import of qgis.core with QgsApplication initializing and data providers loaded.",[76,77],"rect",{"x":78,"y":78,"width":79,"height":80,"fill":81},"0","760","410","#f6f3ea",[83,84,90],"text",{"x":85,"y":86,"style":87,"fill":88,"textAnchor":89},"20","28","text-anchor:start;font-family:sans-serif;font-size:16px;font-weight:bold","#17211d","start","Two Windows install paths — both end at a working import",[76,92],{"x":93,"y":94,"width":95,"height":96,"rx":97,"fill":98,"stroke":99,"style":100},"210","44","340","58","10","#fffdf7","#0f766e","stroke-width:2.5",[83,102,107],{"x":103,"y":104,"style":105,"fill":88,"textAnchor":106},"380","69","text-anchor:middle;font-family:sans-serif;font-size:14px;font-weight:bold","middle","Do you need PyQGIS to run",[83,109,111],{"x":103,"y":110,"style":105,"fill":88,"textAnchor":106},"88","outside QGIS Desktop?",[113,114],"path",{"d":115,"fill":116,"stroke":117,"style":118},"M210,73 H120 V148","none","#2f3b35","stroke-width:2.5;marker-end:url(#winArrow)",[83,120,125],{"x":121,"y":122,"style":123,"fill":124,"textAnchor":89},"150","66","text-anchor:start;font-family:sans-serif;font-size:12px;font-weight:bold","#b45309","NO",[113,127],{"d":128,"fill":116,"stroke":117,"style":100},"M380,102 V128 H630",[83,130,134],{"x":131,"y":132,"style":123,"fill":133,"textAnchor":89},"392","120","#15803d","YES",[113,136],{"d":137,"fill":116,"stroke":117,"style":118},"M400,128 V150",[113,139],{"d":140,"fill":116,"stroke":117,"style":118},"M630,128 V150",[76,142],{"x":143,"y":121,"width":144,"height":145,"rx":146,"fill":98,"stroke":124,"style":100},"30","180","104","9",[83,148,151],{"x":132,"y":149,"style":150,"fill":124,"textAnchor":106},"176","text-anchor:middle;font-family:sans-serif;font-size:13px;font-weight:bold","Nothing to install",[83,153,156],{"x":132,"y":154,"style":155,"fill":117,"textAnchor":106},"202","text-anchor:middle;font-family:sans-serif;font-size:11px","The built-in Python",[83,158,160],{"x":132,"y":159,"style":155,"fill":117,"textAnchor":106},"218","Console already loads",[83,162,25],{"x":132,"y":163,"style":164,"fill":88,"textAnchor":106},"238","text-anchor:middle;font-family:monospace;font-size:11px",[76,166],{"x":167,"y":121,"width":168,"height":145,"rx":146,"fill":98,"stroke":133,"style":100},"290","220",[83,170,173],{"x":171,"y":172,"style":150,"fill":133,"textAnchor":106},"400","174","Method 1 · OSGeo4W",[83,175,178],{"x":171,"y":176,"style":177,"fill":133,"textAnchor":106},"191","text-anchor:middle;font-family:sans-serif;font-size:12px;font-weight:bold","Network Installer",[83,180,183],{"x":171,"y":181,"style":182,"fill":117,"textAnchor":106},"215","text-anchor:middle;font-family:sans-serif;font-size:10.5px","Auto-registers",[83,185,188],{"x":171,"y":186,"style":187,"fill":88,"textAnchor":106},"231","text-anchor:middle;font-family:monospace;font-size:10.5px","QGIS_PREFIX_PATH,",[83,190,192],{"x":171,"y":191,"style":187,"fill":88,"textAnchor":106},"245","PYTHONPATH, PATH",[76,194],{"x":195,"y":121,"width":93,"height":145,"rx":146,"fill":98,"stroke":99,"style":100},"525",[83,197,199],{"x":198,"y":172,"style":150,"fill":99,"textAnchor":106},"630","Method 2 · Standalone",[83,201,202],{"x":198,"y":176,"style":177,"fill":99,"textAnchor":106},"Installer",[83,204,205],{"x":198,"y":181,"style":182,"fill":117,"textAnchor":106},"You set paths via",[83,207,208],{"x":198,"y":186,"style":187,"fill":88,"textAnchor":106},"run_pyqgis.bat",[83,210,212],{"x":198,"y":211,"style":182,"fill":117,"textAnchor":106},"247","(per session)",[113,214],{"d":215,"fill":116,"stroke":117,"style":100},"M400,254 V292",[113,217],{"d":218,"fill":116,"stroke":117,"style":100},"M630,254 V292",[113,220],{"d":221,"fill":116,"stroke":117,"style":100},"M400,292 H630",[113,223],{"d":224,"fill":116,"stroke":117,"style":118},"M515,292 V316",[76,226],{"x":227,"y":228,"width":229,"height":230,"rx":97,"fill":231,"stroke":88,"style":100},"355","316","320","76","#26322d",[83,233,238],{"x":234,"y":235,"style":236,"fill":237,"textAnchor":106},"515","346","text-anchor:middle;font-family:monospace;font-size:14px;font-weight:bold","#d9f99d","import qgis.core  ✓",[83,240,243],{"x":234,"y":241,"style":242,"fill":237,"textAnchor":106},"370","text-anchor:middle;font-family:sans-serif;font-size:11.5px","QgsApplication starts, data providers load",[245,246,247],"defs",{},[248,249,255],"marker",{"id":250,"markerWidth":97,"markerHeight":97,"refX":251,"refY":252,"orient":253,"markerUnits":254},"winArrow","8","3","auto","strokeWidth",[113,256],{"d":257,"fill":117},"M0,0 L8,3 L0,6 Z",[259,260,262],"h2",{"id":261},"prerequisites","Prerequisites",[14,264,265],{},"Confirm each of these before installing — most \"it won't import\" reports on Windows trace back to a mismatch in this list rather than a broken install:",[267,268,269,276,282,292,306,319],"ul",{},[270,271,272,275],"li",{},[18,273,274],{},"OS:"," Windows 10\u002F11 64-bit only (32-bit was deprecated in QGIS 3.20).",[270,277,278,281],{},[18,279,280],{},"QGIS version:"," 3.44 LTR (recommended) or 4.0+ current.",[270,283,284,287,288,291],{},[18,285,286],{},"Python version:"," whatever ships ",[56,289,290],{},"with"," your QGIS — 3.12 for QGIS 3.34 and later (including 3.44 LTR); older releases such as 3.28 LTR bundled 3.9. You cannot substitute a separately installed Python.",[270,293,294,297,298,301,302,305],{},[18,295,296],{},"Architecture:"," strictly 64-bit throughout. Mixing a 32-bit Python with 64-bit QGIS DLLs raises ",[23,299,300],{},"ImportError"," on the first ",[23,303,304],{},"import qgis.core",".",[270,307,308,311,312,315,316,318],{},[18,309,310],{},"Permissions:"," administrator rights are needed only when the installer writes machine-level ",[23,313,314],{},"PATH"," \u002F ",[23,317,49],{}," entries. A per-session launcher works without elevation.",[270,320,321,324,325,327,328,305],{},[18,322,323],{},"Environment conflicts:"," a standalone Anaconda\u002FMiniconda base environment on the ",[23,326,314],{}," frequently shadows the QGIS libraries. Keep conda deactivated, or isolate work in a dedicated environment as described in ",[42,329,331],{"href":330},"\u002Fpyqgis-fundamentals-environment-setup\u002Fvirtual-environments-for-gis\u002F","Virtual Environments for GIS",[259,333,335],{"id":334},"method-1-osgeo4w-network-installer-recommended","Method 1: OSGeo4W Network Installer (recommended)",[14,337,338],{},"The OSGeo4W installer is the path that requires no manual path surgery — it wires up the environment for you.",[340,341,342,349,360,373,398],"ol",{},[270,343,344,345,348],{},"Download the ",[18,346,347],{},"OSGeo4W Network Installer (64-bit)"," from the official QGIS download page.",[270,350,351,352,355,356,359],{},"Run it, choose ",[23,353,354],{},"Install from Internet",", and accept the default root (",[23,357,358],{},"C:\\OSGeo4W","). Avoid spaces or special characters anywhere in the install path — they break several downstream scripts.",[270,361,362,363,366,367,370,371,305],{},"In the package selection screen, expand ",[23,364,365],{},"Desktop"," and check ",[23,368,369],{},"qgis-ltr"," (recommended) or ",[23,372,53],{},[270,374,375,376,379,380,383,384,26,387,390,391,26,394,397],{},"Expand ",[23,377,378],{},"Libs"," → ",[23,381,382],{},"Python"," and verify ",[23,385,386],{},"python3-qgis",[23,388,389],{},"python3-qgis-common"," are selected. Dependencies such as ",[23,392,393],{},"gdal-python",[23,395,396],{},"numpy"," auto-select.",[270,399,400,401,26,404,406,407,410,411,305],{},"Complete the install. OSGeo4W registers ",[23,402,403],{},"QGIS_PREFIX_PATH",[23,405,49],{}," and prepends the QGIS ",[23,408,409],{},"bin"," directories to your ",[23,412,314],{},[414,415,417],"h3",{"id":416},"verify-the-bindings","Verify the bindings",[14,419,420],{},"Launch the QGIS-managed Python shell so system Python cannot interfere:",[422,423,428],"pre",{"className":424,"code":425,"language":426,"meta":427,"style":427},"language-cmd shiki shiki-themes github-dark","C:\\OSGeo4W\\bin\\python-qgis-ltr.bat\n","cmd","",[23,429,430],{"__ignoreMap":427},[431,432,435],"span",{"class":433,"line":434},"line",1,[431,436,425],{},[14,438,439,440,447],{},"Then run this headless verification script. It initializes a full ",[42,441,443,444],{"href":442},"\u002Fpyqgis-fundamentals-environment-setup\u002Fvirtual-environments-for-gis\u002Frunning-python-scripts-outside-qgis-desktop\u002F","standalone ",[23,445,446],{},"QgsApplication"," — the same bootstrap every off-desktop script uses — and creates a throwaway memory layer to prove the data providers loaded:",[422,449,453],{"className":450,"code":451,"language":452,"meta":427,"style":427},"language-python shiki shiki-themes github-dark","import qgis.core\nfrom qgis.core import QgsApplication\n\nprint(f\"PyQGIS loaded: {qgis.core.Qgis.QGIS_VERSION}\")\n\n# Match your installation type: qgis-ltr or qgis\nQgsApplication.setPrefixPath(\"C:\u002FOSGeo4W\u002Fapps\u002Fqgis-ltr\", True)\nqgs = QgsApplication([], False)\nqgs.initQgis()\n\nlayer = qgis.core.QgsVectorLayer(\"Point\", \"temp\", \"memory\")\nprint(f\"Test layer valid: {layer.isValid()}\")\n\nqgs.exitQgis()\n","python",[23,454,455,465,479,486,518,523,530,547,564,570,575,601,625,630],{"__ignoreMap":427},[431,456,457,461],{"class":433,"line":434},[431,458,460],{"class":459},"snl16","import",[431,462,464],{"class":463},"s95oV"," qgis.core\n",[431,466,468,471,474,476],{"class":433,"line":467},2,[431,469,470],{"class":459},"from",[431,472,473],{"class":463}," qgis.core ",[431,475,460],{"class":459},[431,477,478],{"class":463}," QgsApplication\n",[431,480,482],{"class":433,"line":481},3,[431,483,485],{"emptyLinePlaceholder":484},true,"\n",[431,487,489,493,496,499,503,506,509,512,515],{"class":433,"line":488},4,[431,490,492],{"class":491},"sDLfK","print",[431,494,495],{"class":463},"(",[431,497,498],{"class":459},"f",[431,500,502],{"class":501},"sU2Wk","\"PyQGIS loaded: ",[431,504,505],{"class":491},"{",[431,507,508],{"class":463},"qgis.core.Qgis.",[431,510,511],{"class":491},"QGIS_VERSION}",[431,513,514],{"class":501},"\"",[431,516,517],{"class":463},")\n",[431,519,521],{"class":433,"line":520},5,[431,522,485],{"emptyLinePlaceholder":484},[431,524,526],{"class":433,"line":525},6,[431,527,529],{"class":528},"sjoCn","# Match your installation type: qgis-ltr or qgis\n",[431,531,533,536,539,542,545],{"class":433,"line":532},7,[431,534,535],{"class":463},"QgsApplication.setPrefixPath(",[431,537,538],{"class":501},"\"C:\u002FOSGeo4W\u002Fapps\u002Fqgis-ltr\"",[431,540,541],{"class":463},", ",[431,543,544],{"class":491},"True",[431,546,517],{"class":463},[431,548,550,553,556,559,562],{"class":433,"line":549},8,[431,551,552],{"class":463},"qgs ",[431,554,555],{"class":459},"=",[431,557,558],{"class":463}," QgsApplication([], ",[431,560,561],{"class":491},"False",[431,563,517],{"class":463},[431,565,567],{"class":433,"line":566},9,[431,568,569],{"class":463},"qgs.initQgis()\n",[431,571,573],{"class":433,"line":572},10,[431,574,485],{"emptyLinePlaceholder":484},[431,576,578,581,583,586,589,591,594,596,599],{"class":433,"line":577},11,[431,579,580],{"class":463},"layer ",[431,582,555],{"class":459},[431,584,585],{"class":463}," qgis.core.QgsVectorLayer(",[431,587,588],{"class":501},"\"Point\"",[431,590,541],{"class":463},[431,592,593],{"class":501},"\"temp\"",[431,595,541],{"class":463},[431,597,598],{"class":501},"\"memory\"",[431,600,517],{"class":463},[431,602,604,606,608,610,613,615,618,621,623],{"class":433,"line":603},12,[431,605,492],{"class":491},[431,607,495],{"class":463},[431,609,498],{"class":459},[431,611,612],{"class":501},"\"Test layer valid: ",[431,614,505],{"class":491},[431,616,617],{"class":463},"layer.isValid()",[431,619,620],{"class":491},"}",[431,622,514],{"class":501},[431,624,517],{"class":463},[431,626,628],{"class":433,"line":627},13,[431,629,485],{"emptyLinePlaceholder":484},[431,631,633],{"class":433,"line":632},14,[431,634,635],{"class":463},"qgs.exitQgis()\n",[14,637,638,639,643],{},"If both lines print and the layer reports valid, module resolution and the GDAL\u002FOGR providers are working. From here you can point an IDE at the same interpreter — see ",[42,640,642],{"href":641},"\u002Fpyqgis-fundamentals-environment-setup\u002Fsetting-up-pycharm-for-qgis\u002F","setting up PyCharm for QGIS development"," for the interpreter and environment-variable configuration.",[259,645,647],{"id":646},"method-2-standalone-installer-manual-configuration","Method 2: Standalone Installer (manual configuration)",[14,649,650,651,654],{},"If corporate firewalls block the OSGeo4W package repository, use the official QGIS Windows Standalone Installer instead. It does ",[18,652,653],{},"not"," auto-register Python paths, so you supply them yourself through a launcher.",[340,656,657,664],{},[270,658,659,660,663],{},"Install the standalone package (default: ",[23,661,662],{},"C:\\Program Files\\QGIS 3.44",").",[270,665,666,667,669],{},"Create a session launcher, ",[23,668,208],{},":",[422,671,675],{"className":672,"code":673,"language":674,"meta":427,"style":427},"language-bat shiki shiki-themes github-dark","@echo off\nset \"QGIS_ROOT=C:\\Program Files\\QGIS 3.44\"\nset \"PATH=%QGIS_ROOT%\\bin;%QGIS_ROOT%\\apps\\qgis\\bin;%PATH%\"\nset \"PYTHONPATH=%QGIS_ROOT%\\apps\\qgis\\python;%QGIS_ROOT%\\apps\\qgis\\python\\plugins;%PYTHONPATH%\"\nset \"QGIS_PREFIX_PATH=%QGIS_ROOT%\\apps\\qgis\"\nset \"PYTHONHOME=%QGIS_ROOT%\\apps\\Python312\"\n\"%QGIS_ROOT%\\bin\\python3.exe\"\n","bat",[23,676,677,682,687,692,697,702,707],{"__ignoreMap":427},[431,678,679],{"class":433,"line":434},[431,680,681],{},"@echo off\n",[431,683,684],{"class":433,"line":467},[431,685,686],{},"set \"QGIS_ROOT=C:\\Program Files\\QGIS 3.44\"\n",[431,688,689],{"class":433,"line":481},[431,690,691],{},"set \"PATH=%QGIS_ROOT%\\bin;%QGIS_ROOT%\\apps\\qgis\\bin;%PATH%\"\n",[431,693,694],{"class":433,"line":488},[431,695,696],{},"set \"PYTHONPATH=%QGIS_ROOT%\\apps\\qgis\\python;%QGIS_ROOT%\\apps\\qgis\\python\\plugins;%PYTHONPATH%\"\n",[431,698,699],{"class":433,"line":520},[431,700,701],{},"set \"QGIS_PREFIX_PATH=%QGIS_ROOT%\\apps\\qgis\"\n",[431,703,704],{"class":433,"line":525},[431,705,706],{},"set \"PYTHONHOME=%QGIS_ROOT%\\apps\\Python312\"\n",[431,708,709],{"class":433,"line":532},[431,710,711],{},"\"%QGIS_ROOT%\\bin\\python3.exe\"\n",[340,713,714],{"start":481},[270,715,716,717,720,721,724,725,728,729,731,732,734],{},"Double-click the batch file. It opens a terminal with PyQGIS importable ",[18,718,719],{},"for that session only",", leaving machine-wide settings untouched. If your build ships a different Python, change ",[23,722,723],{},"Python312"," to match the folder under ",[23,726,727],{},"apps\\",", and swap ",[23,730,53],{}," for ",[23,733,369],{}," in the paths if you installed the LTR variant. Run the same verification script above to confirm.",[259,736,738],{"id":737},"what-the-two-installers-actually-give-you","What the two installers actually give you",[14,740,741],{},"The choice between them is not about ease of installation but about whether you will ever need to add a package or run a script outside the application.",[14,743,744],{},[61,745,748,751,754,757,762,768,774,778,782,829],{"viewBox":746,"role":64,"ariaLabel":747,"xmlns":66},"0 0 760 244","A comparison of the OSGeo4W network installer and the standalone installer across package management, multiple versions, environment scripts and suitability for development",[68,749,750],{},"OSGeo4W versus the standalone installer",[72,752,753],{},"The network installer provides a package manager, allows several QGIS versions side by side, ships environment scripts that configure paths, and suits development. The standalone installer is a single fixed bundle with no package manager, one version at a time, and manual environment configuration, and suits a desktop user who will never script.",[76,755],{"x":78,"y":78,"width":79,"height":756,"fill":81},"244",[83,758,761],{"x":103,"y":759,"style":760,"fill":88,"textAnchor":106},"26","text-anchor:middle;font-size:14px;font-weight:bold;font-family:sans-serif","Pick by what you will do next, not by download size",[433,763],{"x1":764,"y1":122,"x2":765,"y2":122,"stroke":766,"style":767},"272","744","#59645f","stroke-width:1.5",[83,769,773],{"x":770,"y":96,"style":771,"fill":88,"textAnchor":772},"260","text-anchor:end;font-size:11.5px;font-weight:bold;font-family:sans-serif","end","capability",[83,775,777],{"x":171,"y":96,"style":776,"fill":133,"textAnchor":106},"text-anchor:middle;font-size:11.5px;font-weight:bold;font-family:sans-serif","OSGeo4W",[83,779,781],{"x":780,"y":96,"style":776,"fill":124,"textAnchor":106},"628","standalone",[783,784,786,791,795,799,803,806,809,813,816,819,823,826],"g",{"style":785},"font-size:11.5px;font-family:sans-serif",[83,787,790],{"x":770,"y":788,"style":789,"fill":117,"textAnchor":772},"96","text-anchor:end","add Python packages",[83,792,794],{"x":171,"y":788,"style":793,"fill":133,"textAnchor":106},"text-anchor:middle;font-weight:bold","✓ package manager",[83,796,798],{"x":780,"y":788,"style":797,"fill":124,"textAnchor":106},"text-anchor:middle","manual pip only",[83,800,802],{"x":770,"y":801,"style":789,"fill":117,"textAnchor":772},"130","several QGIS versions",[83,804,805],{"x":171,"y":801,"style":793,"fill":133,"textAnchor":106},"✓ side by side",[83,807,808],{"x":780,"y":801,"style":797,"fill":124,"textAnchor":106},"one at a time",[83,810,812],{"x":770,"y":811,"style":789,"fill":117,"textAnchor":772},"164","environment scripts",[83,814,815],{"x":171,"y":811,"style":793,"fill":133,"textAnchor":106},"✓ o4w_env.bat",[83,817,818],{"x":780,"y":811,"style":797,"fill":124,"textAnchor":106},"set the vars yourself",[83,820,822],{"x":770,"y":821,"style":789,"fill":117,"textAnchor":772},"198","suits",[83,824,825],{"x":171,"y":821,"style":793,"fill":133,"textAnchor":106},"development",[83,827,828],{"x":780,"y":821,"style":797,"fill":124,"textAnchor":106},"desktop use only",[83,830,832],{"x":103,"y":831,"style":776,"fill":133,"textAnchor":106},"232","choose OSGeo4W if any PyQGIS is in your future",[259,834,836],{"id":835},"the-environment-variables-that-matter","The environment variables that matter",[14,838,839],{},"Four variables have to be right before the bindings will import, and the OSGeo4W shell sets all four for you — which is precisely why it is the recommended route.",[14,841,842],{},[61,843,846,849,852,855,867,870,878,883,887,890,893,897,900,903,907,911,916,918,922,924,928,934,937,940],{"viewBox":844,"role":64,"ariaLabel":845,"xmlns":66},"0 0 760 236","Four environment variables — PYTHONPATH, PATH, QGIS_PREFIX_PATH and GDAL_DATA — with what each one lets Python find",[68,847,848],{},"The four variables the bindings need",[72,850,851],{},"PYTHONPATH points at the QGIS python directory so the modules can be found. PATH points at the bin directory so the compiled libraries load. QGIS_PREFIX_PATH tells QGIS where its resources live. GDAL_DATA points at the projection and format definitions. The OSGeo4W shell sets all four before launching anything.",[76,853],{"x":78,"y":78,"width":79,"height":854,"fill":81},"236",[245,856,857],{},[248,858,864],{"id":859,"viewBox":860,"refX":251,"refY":861,"markerWidth":862,"markerHeight":862,"orient":863},"winEnvArrow","0 0 10 10","5","7","auto-start-reverse",[113,865],{"d":866,"fill":99},"M0 0 L10 5 L0 10 z",[83,868,869],{"x":103,"y":759,"style":760,"fill":88,"textAnchor":106},"Miss one and the failure looks like a different problem",[76,871],{"x":872,"y":873,"width":874,"height":875,"rx":251,"fill":98,"stroke":876,"style":877},"16","50","264","46","#2563eb","stroke-width:2",[83,879,49],{"x":880,"y":881,"style":882,"fill":876},"36","70","font-size:11px;font-weight:bold;font-family:monospace",[83,884,886],{"x":880,"y":110,"style":885,"fill":117},"font-size:10.5px;font-family:sans-serif","…\\apps\\qgis\\python",[76,888],{"x":872,"y":889,"width":874,"height":875,"rx":251,"fill":98,"stroke":99,"style":877},"106",[83,891,314],{"x":880,"y":892,"style":882,"fill":99},"126",[83,894,896],{"x":880,"y":895,"style":885,"fill":117},"144","…\\apps\\qgis\\bin;…\\bin",[76,898],{"x":872,"y":899,"width":874,"height":875,"rx":251,"fill":98,"stroke":124,"style":877},"162",[83,901,403],{"x":880,"y":902,"style":882,"fill":124},"182",[83,904,906],{"x":880,"y":905,"style":885,"fill":117},"200","…\\apps\\qgis",[76,908],{"x":909,"y":873,"width":764,"height":875,"rx":251,"fill":98,"stroke":766,"style":910},"472","stroke-width:1.6",[83,912,915],{"x":913,"y":914,"style":885,"fill":117},"490","78","Python can find the modules",[76,917],{"x":909,"y":889,"width":764,"height":875,"rx":251,"fill":98,"stroke":766,"style":910},[83,919,921],{"x":913,"y":920,"style":885,"fill":117},"134","the compiled DLLs load",[76,923],{"x":909,"y":899,"width":764,"height":875,"rx":251,"fill":98,"stroke":766,"style":910},[83,925,927],{"x":913,"y":926,"style":885,"fill":117},"190","QGIS finds its own resources",[433,929],{"x1":930,"y1":931,"x2":932,"y2":931,"stroke":99,"style":933},"280","73","468","stroke-width:2;marker-end:url(#winEnvArrow)",[433,935],{"x1":930,"y1":936,"x2":932,"y2":936,"stroke":99,"style":933},"129",[433,938],{"x1":930,"y1":939,"x2":932,"y2":939,"stroke":99,"style":933},"185",[83,941,944],{"x":103,"y":942,"style":943,"fill":766,"textAnchor":106},"228","text-anchor:middle;font-size:11px;font-family:sans-serif","the OSGeo4W shell sets all of these before it launches anything",[259,946,948],{"id":947},"qgis-version-compatibility-notes","QGIS-version compatibility notes",[14,950,951],{},"The bindings are compiled against the exact Python, GDAL, PROJ, and Qt versions bundled with each QGIS release, so version alignment is not optional:",[267,953,954,967,987],{},[270,955,956,959,960,963,964,305],{},[18,957,958],{},"QGIS 3.34 LTR \u002F 3.44 LTR:"," Python 3.12, Qt 5. The examples on this page are pinned here. The launcher name is ",[23,961,962],{},"python-qgis-ltr.bat"," and the prefix path ends in ",[23,965,966],{},"apps\u002Fqgis-ltr",[270,968,969,972,973,975,976,978,979,982,983,986],{},[18,970,971],{},"QGIS 4.0+:"," Qt 6 and a newer Python; the ",[23,974,369],{}," suffix becomes ",[23,977,53],{},", so use ",[23,980,981],{},"python-qgis.bat"," and the ",[23,984,985],{},"apps\u002Fqgis"," prefix.",[270,988,989,992,993,996],{},[18,990,991],{},"QGIS 3.28 LTR and older:"," shipped Python 3.9. Methods that appeared in later APIs will raise ",[23,994,995],{},"AttributeError"," here.",[14,998,999,1000,1004],{},"Because method names and enum locations drift between releases, cross-check any snippet against your installed version using the ",[42,1001,1003],{"href":1002},"\u002Fpyqgis-fundamentals-environment-setup\u002Fqgis-api-architecture\u002Fqgis-python-version-compatibility-guide\u002F","QGIS Python version compatibility guide"," before assuming it will run. Always drive external scripts with the interpreter that matches the QGIS build whose libraries they import — never a system or conda Python.",[259,1006,1008],{"id":1007},"troubleshooting","Troubleshooting",[267,1010,1011,1028,1047,1067],{},[270,1012,1013,1018,1019,1021,1022,1024,1025,1027],{},[18,1014,1015],{},[23,1016,1017],{},"DLL load failed while importing qgis.core"," — the Visual C++ Redistributable (2015–2022) is missing, or the ",[23,1020,314],{}," resolves a conflicting DLL first. Install the latest VC++ runtime and make sure the QGIS ",[23,1023,409],{}," directories precede any system Python paths. Launching through ",[23,1026,962],{}," sidesteps most ordering issues because it sets the environment for you.",[270,1029,1030,1035,1036,1038,1039,1042,1043,305],{},[18,1031,1032],{},[23,1033,1034],{},"ModuleNotFoundError: No module named 'qgis'"," — the interpreter cannot see ",[23,1037,49],{},", usually because an IDE points at a plain system Python. Point it at ",[23,1040,1041],{},"C:\\OSGeo4W\\bin\\python-qgis-ltr.bat",", or work through the deeper diagnosis in ",[42,1044,1046],{"href":1045},"\u002Fpyqgis-fundamentals-environment-setup\u002Fdebugging-pyqgis-scripts\u002Ffixing-pyqgis-module-import-errors\u002F","fixing PyQGIS module import errors",[270,1048,1049,1052,1053,26,1056,1059,1060,1063,1064,305],{},[18,1050,1051],{},"Proxy \u002F network timeouts during install"," — set ",[23,1054,1055],{},"http_proxy",[23,1057,1058],{},"https_proxy"," before launching OSGeo4W, or download the ",[23,1061,1062],{},".msi"," packages manually and choose ",[23,1065,1066],{},"Install from Local Directory",[270,1068,1069,1072,1073,1076,1077,1080,1081,1084],{},[18,1070,1071],{},"Third-party packages invisible to PyQGIS"," — install libraries such as ",[23,1074,1075],{},"pandas"," or ",[23,1078,1079],{},"requests"," through the bundled shell (",[23,1082,1083],{},"python-qgis-ltr.bat -m pip install \u003Cpackage>",") so they land in the QGIS interpreter's site-packages and match its ABI. Installing into a system or conda Python leaves them unimportable from PyQGIS.",[259,1086,1088],{"id":1087},"conclusion","Conclusion",[14,1090,1091,1092,1094,1095,1097,1098,1100,1101,1103],{},"On Windows, reliable PyQGIS bindings come from installing QGIS itself — through OSGeo4W when you can reach its repository, or the standalone installer with a ",[23,1093,208],{}," launcher when you cannot — and never from ",[23,1096,36],{},". Once the headless verification script prints a version and a valid layer, the same interpreter is ready to drive IDEs, scheduled jobs, and standalone tools. From here, move into the interactive ",[42,1099,45],{"href":44}," to explore the API live, then formalize your setup with ",[42,1102,331],{"href":330}," for reproducible builds.",[259,1105,1107],{"id":1106},"frequently-asked-questions","Frequently Asked Questions",[14,1109,1110,1116,1117,1120],{},[18,1111,1112,1113,1115],{},"Why can't I just run ",[23,1114,36],{}," to get the bindings on Windows?","\nThe PyPI ",[23,1118,1119],{},"pyqgis"," package is a documentation stub with no compiled binaries, so it cannot satisfy the C++ dependencies PyQGIS requires. The bindings are tightly coupled to QGIS's bundled GDAL, PROJ, and Qt builds, which must be installed together. Use the OSGeo4W Network Installer or the standalone installer so the binaries and their versions match exactly.",[14,1122,1123,1126,1127,1129],{},[18,1124,1125],{},"Which Python version do the QGIS Windows bindings require?","\nQGIS 3.34 and later, including 3.44 LTR, bundle Python 3.12, while older releases such as 3.28 LTR shipped Python 3.9. You must use the interpreter that ships with your QGIS install rather than a separately installed Python, because the compiled modules are built against that specific version. Mixing versions produces ",[23,1128,300],{}," or ABI mismatch failures.",[14,1131,1132,1135,1136,1139],{},[18,1133,1134],{},"How do I install third-party packages like pandas into the QGIS Python environment?","\nRun pip through the bundled shell, for example ",[23,1137,1138],{},"python-qgis-ltr.bat -m pip install pandas",", so packages land in the QGIS interpreter's site-packages. Installing into a system or conda Python instead leaves them invisible to PyQGIS and risks ABI conflicts. Always confirm the install used the OSGeo4W Python before importing the package in a script.",[14,1141,1142,1148,1149,1151,1152,1154,1155,1157],{},[18,1143,1144,1145,1147],{},"What causes ",[23,1146,1017],{}," on Windows?","\nThis usually means the Visual C++ Redistributable (2015–2022) is missing or the system ",[23,1150,314],{}," resolves a conflicting DLL before the QGIS one. Install the latest VC++ runtime and ensure the QGIS ",[23,1153,409],{}," directories appear ahead of any system Python paths. Launching through ",[23,1156,962],{}," sidesteps most ordering problems because it sets the environment for you.",[14,1159,1160,1163,1164,26,1166,1168,1169,1171],{},[18,1161,1162],{},"Do I need administrator rights to install the bindings?","\nAdministrator privileges are needed when the installer registers system-level ",[23,1165,314],{},[23,1167,49],{}," entries. If you cannot elevate, you can still use the bundled ",[23,1170,962],{}," launcher or a per-session batch file that sets the variables for that shell only. This keeps PyQGIS working without modifying machine-wide environment settings.",[259,1173,1175],{"id":1174},"related","Related",[267,1177,1178,1187,1193,1199,1209,1215],{},[270,1179,1180,1183,1184,1186],{},[18,1181,1182],{},"Up:"," ",[42,1185,45],{"href":44}," — the parent guide to the interactive console the bindings power.",[270,1188,1189,1192],{},[42,1190,1191],{"href":442},"Running Python Scripts Outside QGIS Desktop"," — the initialization pattern for the interpreter you just configured.",[270,1194,1195,1198],{},[42,1196,1197],{"href":641},"Setting Up PyCharm for QGIS Development"," — point a full IDE at the OSGeo4W interpreter.",[270,1200,1201,1204,1205,1208],{},[42,1202,1203],{"href":1045},"Fixing PyQGIS Module Import Errors"," — diagnose ",[23,1206,1207],{},"ModuleNotFoundError"," and DLL failures in depth.",[270,1210,1211,1214],{},[42,1212,1213],{"href":330},"Virtual Environments for QGIS and PyQGIS"," — isolate dependencies for reproducible builds.",[270,1216,1217,1183,1220,1224],{},[18,1218,1219],{},"Up one level:",[42,1221,1223],{"href":1222},"\u002Fpyqgis-fundamentals-environment-setup\u002F","PyQGIS Fundamentals & Environment Setup"," — the full environment reference.",[1226,1227,1228],"style",{},"html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html pre.shiki code .snl16, html code.shiki .snl16{--shiki-default:#F97583}html pre.shiki code .s95oV, html code.shiki .s95oV{--shiki-default:#E1E4E8}html pre.shiki code .sDLfK, html code.shiki .sDLfK{--shiki-default:#79B8FF}html pre.shiki code .sU2Wk, html code.shiki .sU2Wk{--shiki-default:#9ECBFF}html pre.shiki code .sjoCn, html code.shiki .sjoCn{--shiki-default:#9AA79F}",{"title":427,"searchDepth":467,"depth":467,"links":1230},[1231,1232,1235,1236,1237,1238,1239,1240,1241,1242],{"id":261,"depth":467,"text":262},{"id":334,"depth":467,"text":335,"children":1233},[1234],{"id":416,"depth":481,"text":417},{"id":646,"depth":467,"text":647},{"id":737,"depth":467,"text":738},{"id":835,"depth":467,"text":836},{"id":947,"depth":467,"text":948},{"id":1007,"depth":467,"text":1008},{"id":1087,"depth":467,"text":1088},{"id":1106,"depth":467,"text":1107},{"id":1174,"depth":467,"text":1175},"Install QGIS Python bindings on Windows step by step. Set up PyQGIS outside QGIS desktop, configure sys.path, and run standalone Python scripts.","md",{"slug":12,"type":1246,"breadcrumb":1247,"datePublished":1248,"dateModified":1249},"article","Install PyQGIS Bindings on Windows","2025-03-04","2026-07-18","\u002Fpyqgis-fundamentals-environment-setup\u002Fqgis-python-console-basics\u002Fhow-to-install-qgis-python-bindings-on-windows",{"title":5,"description":1243},"pyqgis-fundamentals-environment-setup\u002Fqgis-python-console-basics\u002Fhow-to-install-qgis-python-bindings-on-windows\u002Findex","qYJOPsOiEEp8kzUmGgFWyajvBgNYStjgGrgWt8r9rFI",1787823360564]