National Instruments is largely known for LabVIEW, which seamlessly integrates NI’s hardware offerings. However, NI recognized that engineers like to use the right tool for the job, and that tool isn’t always LabVIEW. Consequently, NI has provided hardware APIs for several languages other than LabVIEW, but there isn’t yet the same depth of documentation for those languages as there is for LabVIEW.
Python currently sits at the top of the heap for data analysis tools, so let’s walk through a quick demo to help you get started with DAQmx in Python. For further reading, here’s a case study that describes how we’ve done something very similar for a client who wanted to integrate NI hardware in their existing Python test framework.
You can get the source code for the demo on GitHub.
Setting Up a Python Environment
Already have Python on your PC? Go ahead and skip this part. We’re going to create a virtual environment with the nidaqmx package installed. For this exercise, I’m assuming that you’ve got a Windows PC with DAQmx and MAX installed already.
- Install python on your system, if it isn’t already installed.
- I prefer to install it from a standalone installer rather than the install manager.
- For this demo, version 3.10 or newer will work just fine.
- When I install, I pick several nonstandard options from the “Customize Installation” menu.
- I do not add python.exe to PATH (I like to explicitly call the version I want to use).
- I do not install the py launcher, for the same reason.
- I do install for all users.
- I put every version in C:\pythons, for example, C:\pythons\python3_10, C:\pythons\python3_12, etc.
- No matter how you choose to install, find the path to the python interpreter (python.exe) that got installed.
- Next, create a virtual environment in the source directory.
- The concept of a “virtual environment” and its many benefits are not in the scope of this blog, but if you’re a beginner, just take my word for it that you want to do this.
- Get the source code from GitHub, then navigate to that directory in PowerShell.
- In PowerShell, run C:\pythons\python3_10\python.exe -m venv venv.
- Replace the path to python.exe with the path you used.
- Activate the virtual environment: .\venv\Scripts\activate.
- Install the required packages from pypi: (venv) PS> pip install -r requirements.txt.
That’s it!
Create a DAQmx Task in NI MAX
First, we will create a simulated device in NI MAX and create a task that acquires data from that device. If you have real NI hardware that you’d prefer to use, create a task that uses it, and I’ll meet you in the next section.
In MAX, right-click “Devices and Interfaces” and then click “Create New.”

Select “Simulated NI-DAQmx Device or Modular Instrument” from the list, then click “Finish.” The “Create Simulated NI-DAQmx Device” window will appear, from which you can select a model. I will choose the cDAQ-9174.

The simulated device will now appear in the list. Click it, then select “Configure Simulated cDAQ Chassis” to add simulated modules.

The “Simulated Chassis Configuration” window will appear, and you can add, say, a 9213 thermocouple module.

Now that you’ve got simulated hardware set up, you can create a DAQmx task the way you ordinarily would. Expand “Data Neighborhood,” then right-click “NI-DAQmx Tasks” and click “Create New NI-DAQmx Task…”

Expand “Acquire Signals,” then “Analog Input,” then “Temperature,” and select “Thermocouple.”

MAX will list every available thermocouple channel on all connected hardware. If you have a lot of attached hardware, look for the 9213 in your simulated cDAQ. Select a single analog input channel (ai0 in this image) and click “Next.”

Then you will be prompted for a task name. I’ll just leave it as the default (“MyTemperatureTask”) and click “Finish.”
The LabVIEW Implementation
The completed VI is available in this GitHub repository (demo.vi). The block diagram looks like this:

I’ll walk through this step-by-step, but I’m assuming that you can already read and understand basic LabVIEW code.
First, I get a reference to my task (MyTemperatureTask) and I configure sample timing. I want the acquisition to run until some condition occurs, so I set it as a continuously sampling task. I set the sample rate to 1000 Hz, and I plan to grab data from the device twice a second (I call this the “acquisition rate,” and set it to 2 Hz).
When you run a continuous task, the “samples per channel” input of the timing VI really means “create a memory buffer large enough for this many samples.” If I plan to sample at 1 kHz and grab data from the buffer every half-second, then nominally every time I grab data, I should get 500 samples. In a perfect world, if I sized the buffer at 500 samples, it would always be full but would never overflow when I go to read the data. In reality, your PC has a lot to manage, so I make my buffer 10x larger than the nominal case (hence the “buffer multiplier”).
Next, I start the task, and I immediately start looping. On every iteration of the loop, I read 500 samples. If there are more available in the buffer, they stay there until the next iteration. If there are fewer available, the DAQmx Read VI will block until they become available (up to the default timeout of 10 seconds). The Read VI therefore throttles the loop so that it runs at 2 Hz and will catch up if it falls behind and samples temporarily pile up in the buffer.
For some reason, simulated temperature tasks provide impossibly low temperatures. Literally. Most of the data is colder than absolute zero. Since the task provides data in degrees Celsius, we’ll do a simple analysis, just waiting for the data to get warm enough to enable molecular motion, then we exit the loop, stop the task, and clean up.
The Python Implementation
The completed script is available in this GitHub repository (demo.py).
To do the same thing in Python that we did in LabVIEW, all we need to do is tip that VI on its side:

We do all the same things in the same order! You can retrieve a reference to your task using
task = PersistedTask(task_name).load()
The nidaqmx.errors module provides a DaqError exception that you can use to ensure the task was found. Next, you can call the task.timing.cfg_samp_clk_timing() method to configure the task timing (note that it’s a method of the timing property of task).

The task is started using task.start(). Nothing interesting there:

The while loop is similarly straightforward. Like the LabVIEW code, we stop looping early if there is an error when we call the DAQmx Read VI. task.read() also uses the same default value for the timeout (10 seconds) as the LabVIEW VI.

Once the loop ends, we just do some cleanup and we’re done!

When you run the demo script in PowerShell, it will look something like this:

Summary
If you already know how to use DAQmx in LabVIEW, then you know how to use the Python API also! The organization of the library is the only difference, with methods like cfg_samp_clk_timing() living in the timing property of the task object. Once you get over that tiny hurdle, you’re all set to acquire and crunch your numbers all in the same place!
Interested in how we use Python in our test systems? Contact us today to learn more.







