Snek – Integrating Python in PowerShell

PowerShell Python Modules

November 14, 2019

quote Discuss this Article

Snek is a cross-platform PowerShell module for integrating with Python. It uses the Python for .NET library to load the Python runtime directly into PowerShell. Using the dynamic language runtime, it can then invoke Python scripts and modules and return the result directly to PowerShell as managed .NET objects.

Installation and Requirements

You can install Snek from the PowerShell Gallery.

Install-Module Snek

Snek includes the Python for .NET binaries for each type of support version of Python and architecture. Currently, Snek supports Python v2.7, v3.5, v3.6 and v3.7. You will need to install Python on the PATH for Snek and Python for .NET to find the Python runtime.

Snek will work anywhere that PowerShell and Python are supported.

Executing Scripts

To execute scripts using Snek, you need to use a combination of Use-Python and Invoke-Python. The Use-Python command initializes the Python runtime while Invoke-Python passes the text to the Python runtime for execution.

Use-Python { Invoke-Python -Code "print('Hello, from Python!')" }

Although this is novel, it’s not the most exciting part of Snek. You could easily call a Python script using the python.exe command line from PowerShell.

Returning Data From Python

Since Python for .NET uses the dynamic language runtime, you need to cast objects from the dynamic type back into a regular .NET type. If you don’t do this, PowerShell will attempt to unwind the object and it will result in an exception. To work around this, all you need to do is pass a type name to the ReturnType parameter for Invoke-Python.

Use-Python {
    Invoke-Python "'Hello'" -ReturnType ([String])
}

Integrating with Python Modules

Python for .NET uses the dynamic language runtime in .NET to produce objects that .NET can interact with from Python. One of the great features is the ability to be able to import a Python package and then invoke functions within it and return the results to PowerShell.

Managing PIPs

You can install and uninstall Python PIPs using the Install-PythonPackage and Uninstall-PythonPackage cmdlets. Just specify the name of the package you would like to manage and it will install it just like Install-Module works for PowerShell.

Install-PythonPackage -Name requests

Invoking Package Functions

You can import a Python package using the Import-PythonPackage cmdlet. You need to store the value in a variable so you can invoke its methods. If you don’t store it in a variable, you will encounter an error. In the following example, we invoke the requests package’s get function and return the request back to PowerShell so that we can check the status code.

Use-Python {
    $requests = Import-PythonPackage -Name "requests" 
    [int]$requests.get("https://ironmansoftware.com/").status_code
}

Using Scopes

If you want to issue multiple commands to the same Python scope, you can use the Use-PythonScope cmdlet. You could then issue a command to import a package and then execute something in that package.

Use-Python {
    Use-PythonScope {
        Invoke-Python -Code "import sys" 
        Invoke-Python -Code "sys.version" -ReturnType ([string]) 
    }
}

Setting .NET Variables in Scopes

You can pass .NET variables into Python by using the Set-PythonVariable cmdlet. You must call this cmdlet from within a Python scope. Here’s an example of defining a PowerShell class and then pass that object into Python and accessing the properties to concatenate a string.

Use-Python {
    Use-PythonScope {
        $Person = [Person]::new()
        $Person.FirstName = "Adam"
        $Person.LastName = "Driscoll"
        Set-PythonVariable -Name "person" -Value $Person

        Invoke-Python -Code "person.FirstName + ' ' + person.LastName" -ReturnType ([string])
    }
}

Conclusion

Snek is a pretty cool way of integrating two great scripting languages together. Please play around and let me know what works and what doesn’t!