0

I have a python script that saves values from a MPU6050 sensor to a csv, and then zips the file. When I run it from Thonny or direct from the command line, it works. When I run from rc.local at startup it shows up as running in 'Task Manager' but the files do not save.

My rc.local:

#
# By default this script does nothing.

# Print the IP address
_IP=$(hostname -I) || true
if [ "$_IP" ]; then
  printf "My IP address is %s\n" "$_IP"
fi

sudo python /home/pi/Code/Prospectus/RecordAcceleration.py &

exit 0

My python script named RecordAcceleration.py stored in /home/pi/Code/Prospectus/:

#This is for Sensor Number
SeNum = 4

import numpy as np
#import matplotlib.pyplot as plt

import mpu6050 as mp
import time
import zipfile
import pandas as pd
import os
path = '/'

sensor = mp.mpu6050(0x68)

start = time.time()

j = 1

GB = 2

if len(os.listdir('/media/pi')) ==0:
    path = '/home/pi/AccelData'
else:
    if not os.path.isdir('/media/pi/' + os.listdir('/media/pi')[0] +'/AccelData'):
        os.mkdir('/media/pi/' + os.listdir('/media/pi')[0] +'/AccelData')
    path = '/media/pi/' + os.listdir('/media/pi')[0] +'/AccelData/'

while GB > 1:
    Results = []
    FileStart = time.time()
    for i in range(60000):
        try:
            gx, gy, gz = sensor.get_accel_data(True)
        except:
            del sensor
            time.sleep(0.01)
            sensor = mp.mpu6050(0x68)
            gx, gy, gz = sensor.get_accel_data(True)
        #tx, ty, tz = sensor.get_gyro_data()
        Results.append([time.strftime('%y%m%d-%H%M%S.')+str(int((time.time()-int(time.time()))*10000%10000)).zfill(4), gx, gy, gz,SeNum])
        time.sleep(0.00001)

    Results = np.matrix(Results)

    NextFileName = '60kPoints-'+time.strftime('%y%m%d-%H%M')+'-s'+str(SeNum)
    
    df = pd.DataFrame(data=Results)
    df.to_csv(NextFileName+'.csv', sep=',', header=False, float_format='%.5f')
    
    print(j, (time.time()-start) / 60.0, NextFileName)
    j+=1

    zip_file = zipfile.ZipFile(path + NextFileName+'.zip', 'w')
    zip_file.write(NextFileName+'.csv', compress_type=zipfile.ZIP_DEFLATED)
    zip_file.close()
    
    os.remove(NextFileName+'.csv')
    
    st = os.statvfs(path)
    bytes_avail = (st.f_bavail * st.f_frsize)
    GB = bytes_avail / 1024 / 1024 / 1024
2
  • Are you sure the path + name is always valid? You seem to be missing a '/' when there's no mounted drive in /media/pi (which most likely is the case when you're using rc.local (personally I wouldn't use rc.local anyway... and no need for sudo in rc.local)
    – Dirk
    Nov 22 '21 at 23:12
  • @Dirk, the missing '/' at the end of the path if no drive was mounted was the issue. The script starts running before the drive is mounted, so that it always runs with no external. That then causes it to use the '/home/pi' directory written wrong. I added a time.sleep(10) after the imports, and now the drive is always mounted when I get to that point, and the code is fixed should a drive not be mounted. Appreciate the help. Thank you Nov 24 '21 at 17:25
1

rc.local has been deprecated for some time - here's one description explaining its current state. You shouldn't use rc.local because it's not supported any longer.

There are two common alternatives for running your script at startup:

1, cron with the @reboot invocation,
2. create a "unit file" to run under systemd

As a general comparison between the two options, cron is simpler, while systemd gives you more control once you've "done your homework"

cron:

Setting up a cron job to run at startup is generally straightforward. Open your crontab for editing:

$ crontab -e

This opens your crontab file in your default editor.

Then add your "job(s)" - for example, to run a Python script named HelloWorld.py located in pi's home directory at start/boot time requires a single line be added to your crontab:

@reboot /usr/bin/python /home/pi/HelloWorld.py

This is all that's needed for a very simple cron job, but complications arise in many real-world applications. I feel that using cron successfully requires an understanding of its limitations - I've tried to summarize those here with solutions that will often overcome these limitations.

I noted that your rc.local command calls your Python script using sudo - suggesting that it must be run with root privileges. If that's the case, you should use the root crontab instead of using sudo in your pi user crontab. You may get away with using sudo in a pi user crontab in Raspberry Pi (due to how user pi is configured), but it won't work properly on most other Unix/Linux systems. Otherwise, using the root crontab is virtually identical to using a user crontab:

$ sudo crontab -e

There are many Q&A here on using cron to schedule jobs - I have answered a few myself.

systemd:

Scheduling a job to run at start/boot time may also be accomplished using what is called a systemd unit file. systemd is considered by some to be a better solution in many cases because it does not have some of cron's limitations. Many would say creating the unit file is more difficult than creating a cron job, but like most new tasks, a little experience will make things considerably easier over time.

I won't try to walk through creation of a unit file, but there are many tutorials available online. There's a brief overview of a unit file creation here that will be useful for RPi users (as RPi is a Debian derivative). There are also numerous Q&A here on RPi SE that may be useful.

1
  • I will try to set it up with a cron job and see if it is more stable. Thank you Nov 24 '21 at 17:22
0

It was a missing '/' in path if no drive is mounted. The drive does not mount until after the script is already running, so it tries to use the /home/pi location, but I had a mistake there. When I run it after boot, it works fine because the drive is mounted. I added a time.sleep(10) after the imports, and that delay is sufficient for the drives to mount.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.