Keeping Project Running While Away

Like anyone who owns cats I am tired of them being in the kitchen and eating things they're not supposed to be eating. So I made a motion activated spray bottle with a servo, a PIR sensor, Elegoo Uno knock off, and a mini breadboard. Nothing fancy just spraying when its activated. I have it plugged in with an AC adapter that I had lying around and it works great. My cats have definitely been avoiding the kitchen more with it in there but, it does not stay active for very long. I set it up tested it with myself for range and sensitivity and it covers the area it needs to cover. When I came back about 30-45 minutes later I was able to walk in with no activation. I checked wiring and nothing came loose so I hit the reset button and it started working again. I did more tests and it worked fine but then it happened again in about an hour and a half.(it worked at 30 minutes bc someone got curious) The time delay and range on the PIR are both set as low as they go. I tested the loop and activation with a println in the serial log so I didn't get more soaked and it seemed to be functioning fine. I'm not sure what I'm doing wrong or if its just my hardware being a knock off and everything is from amazon. I got most of the code help from https://arduinogetstarted.com/tutorials/arduino-motion-sensor

#include <Servo.h>
Servo spray;
const int PIN_TO_SENSOR = 2;   // the pin that OUTPUT pin of sensor is connected to
int pinStateCurrent   = LOW; // current state of pin
int pinStatePrevious  = LOW; // previous state of pin
int restpos= 0;
int activepos= 75;
int delaybetween= 500; //delay between sprays
int delayreset= 800; //delay between active and rest pos
void setup() {
  Serial.begin(9600);            // initialize serial
  pinMode(PIN_TO_SENSOR, INPUT); 
spray.attach(3);
spray.write(restpos);
}

void loop() {
  pinStatePrevious = pinStateCurrent; // store old state
  pinStateCurrent = digitalRead(PIN_TO_SENSOR);   // read new state

  if (pinStatePrevious == LOW && pinStateCurrent == HIGH) { 
    Serial.println("DETECTED!");
spray.write(restpos);
delay(delayreset);
spray.write(activepos);
delay(delaybetween);

spray.write(restpos);
delay(delayreset);
spray.write(activepos);
delay(delaybetween);

spray.write(restpos);
delay(delayreset);
spray.write(activepos);
delay(delaybetween);
spray.write(restpos);
  }
  else 
  if (pinStatePrevious == HIGH && pinStateCurrent == LOW) {   // pin state change: HIGH -> LOW
    Serial.println("Motion stopped!");
    spray.write(restpos);
  }
 delay(2000);
}

TYIA

First thing I would look at is the power supply, maybe try a different one and see if it still happens

Put some serial prints in to see where the code stops. That may give some clue to what is going on.

You are not powering the servo with the Arduino are you? No Arduino is a power supply. You should have an external supply for the servo. Connect the grounds.

+1

And log them in something with timestamps

Also might look into using the watchdog timer. It would be best to find the cause (I think it's power), but a watchdog might help.

I added an external power supply and now it’s not even trying to work. I’ll redo the serial print and see if something decided to go wrong there. I’ll check out the watchdog I’ve never used one before.

What are the specs of the external supply (voltage, current capability)?

Please show your connections. A hand drawn schematic is preferred over a fritzing type of diagram. Include all pin names/numbers, components, their part numbers and/or values and power supplies.

If you changed your code, please post the new version so that we can keep up.

I redid the serial prints and everything seems to be working with the code and sensor. I discovered that the servo attached to the project and the one I used to test no longer work. I found a 3rd and it all seems to be functional with the external source but, I am going to make a few adjustments for water protection. Only time will tell if it actually keeps working though.

I found that the cheap mini servos do not like to be stalled. And it does not take long for them to die. I killed 3 or so before i realized that. So now I don't let them go all the way to 0 or 180. I keep minimum greater than 10 and maximun less than 170.

perhaps a snail cam might be better?

A small gear motor to drive the cam and microswitch to sense cam position. The motor would need a transistor driver. More complex but, I would think, more reliable.

When I have a critical project I use a watchdog that is external and kills the power to the project then powers it back up again. The sequence is many seconds long. The reason I have experienced many times where the external hardware locks up and only a power cycle will clear the problem.

You're going to make a cat do what?
cat