Forum Archive

Running simple script in background

gums

I'm trying to execute a simple script in Python via my iPhone in order to keep alive a Buffalo NAS drive by sending a magic packet every 3 minutes. The script works well as long as I have the Python app open in the foreground but as soon as it moves to the background it looks like it stops executing and the NAS turns off.

Is this a limitation of iOS rather than the python app(s) I'm using? Running on android via QPython in the background seems to work well

omz

This is a limitation/feature of iOS. Apps can only run in the background for a couple of minutes before they're suspended by the system, in order to conserve system resources (and improve battery life).

ccc

It would be a nice use case for a Raspberry Pi Zero W ;-)

gums

@omz many thanks for the confirmation, i can now stop wasting time trying to figure a workaround on ios and use Android.

gums

@ccc I'm presuming you mean in such a way as using something like VNC on the iPhone to connect to the Pi and trigger the python script on the Pi which is connected to the home network?

ccc

Either that or maybe even more simply on the Pi just run a script of the form:

import time

while True:  # This minimum viable script runs 24 * 7 * 365
    send_magic_bytes()
    time.sleep(3 * minutes)
mikael

I use crontab on Zero W to run a periodical Python script, in my case storing temperature data from several sensors to the cloud.

My Zero W does not have a screen or a keyboard, but development experience was nice anyway with a Pythonista action that uses ssh to dump the script to Pi W and run it.

kaan191

Hello,

First post here. But have been quietly admiring all the contributions from some of the heroes of this forum. (@mikael, having particularly a lot of fun with your JSWrapper for webviews! I scrape a lot...).

Anyway, I'm not trying to bring this topic back to life, rather, I'm curious if you @mikael have any example scripts of how you communicated with a remote Raspberry Pi server?

I've just bought a Pi 4 (for my kid, but also for me really) and haven't managed to spend much time with it yet.

The use case I'm trying to explore is whether I can send commands (via Pythonista or some other way) to get scripts to run on a remote Pi device. I have Blink Shell (also a nice app) but as I understand it the session closes when the app closes or is too long in the background, and I need it to keep running.

Warning: I'm very much an amateur in all these matters so forgive me if what I'm asking / saying seems dumb.

cvp

@kaan191 Welcome in this marvelous forum full of marvelous guys using this marvelous app.
I wonder if I don't use this word too much 🙄, but ok, wisely.

Anyway, I have also used a Raspberry, before I can connect an USB key on my iPad, and I used SSH to connect Pythonista to my Raspberry. You can launch any command, for instance, I used to eject my USB key, via a command = 'sudo umount /media/pi/....'

mikael

@kaan191, good to hear you are having fun! I have been a bit quiet here lately, which just means I have a ”hot Pythonista project” on that takes up most of my time.

See below for the script I used to communicate with my Pi. I have it configured in Pythonista actions in three different modes:

  1. Move this file to Pi
  2. Move this directory to Pi
  3. Run this file on Pi – move the file, run it, and show the output in Pythonista.
#coding: utf-8
import paramiko
import editor, console
import os.path
import sys

console.clear()

local_path = editor.get_path()
remote_path = os.path.basename(local_path)
local_dir_path = os.path.dirname(local_path)
remote_dir_path = local_dir_path.split('/')[-1]

print('Open SSH connection')
s = paramiko.SSHClient()
s.set_missing_host_key_policy(paramiko.AutoAddPolicy())
s.connect(<local IP address>, 22, username=<username>, password=<password>, timeout=4)
sftp = s.open_sftp()

fixed_local_root = None
fixed_remote_root = <target dir under root on Pi>
try:
  sftp.mkdir(fixed_remote_root)
except:
  pass # Ok if already exists

if sys.argv[1] == 'dir':
  print('--- Send directory')

  #sftp.put(local_dir_path, remote_dir_path)
  #parent = os.path.split(local_dir_path)[1]
  prefix_len = len(local_dir_path)
  for walker in os.walk(local_dir_path):
    remote_sftp_path = remote_dir_path +  walker[0][prefix_len:]
    if remote_sftp_path.endswith('/'):
      remote_sftp_path = remote_sftp_path[:-1]
    try:
      pass
      #sftp.mkdir(os.path.join(remotepath, walker[0]))
    except:
      pass
    for file in walker[2]:
      print('put', os.path.join(walker[0],file), remote_sftp_path + '/' + file)
      #sftp.put(os.path.join(walker[0],file),os.path.join(remotepath,walker[0],file))
else:
  print('--- Send file')
  sftp.put(local_path, remote_path)

if sys.argv[1] == 'run':

  print('--- Run it')
  stdin, stdout, stderr = s.exec_command('python3 ' + remote_path)

  for line in stdout.readlines():
    print(line.rstrip('\n'))

  s.close()

  print('--- Done')

  for line in stderr.readlines():
    print('ERROR:', line.rstrip('\n'))

print('--- Complete')
kaan191

Brilliant @mikael thanks so much for sharing.

I'll dig into this and post back if I run into trouble.