Arduino data logger save and retrieve over bluetooth issue

Hi, I have written a code to use a vibration sensor as an uptime/downtime tracker for a machine to work alongside Simple Time Tracker APP which requires imported data to be in a very specific format "activity", yyyy-MM-dd HH:mm:ss, "Comment, comment" so in this code the information I recieve over the bluetooth serial terminal app is different from the information I view on the wired serial data logger. I am trying to create a save file to the arduino to log the formatted bluetooth data and retrieve it with an RQD command without having to have the bluetooth serial terminal app open and running a continuous log to a .csv file on my phone.

#include <BluetoothSerial.h>
#include <WiFi.h>
#include <BLEDevice.h>
#include <BLEServer.h>
#include <BLEUtils.h>
#include <BLE2902.h>
#include <SPI.h>
#include <time.h>
#include <SPIFFS.h>

BLEServer* pServer = NULL;
BLECharacteristic* pTxCharacteristic;
bool deviceConnected = false;
bool oldDeviceConnected = false;
uint8_t txValue = 0;

const char* ssid = "";
const char* password = "";
const char* ntpServer = "pool.ntp.org";
const long gmtOffset_sec = -25200;
const int daylightOffset_sec = 3600;
const char* DATA_FILE = "/press_data.csv";
bool fileSystemInitialized = false;
bool pressInProgress = false;

#define SERVICE_UUID ""
#define CHARACTERISTIC_UUID_RX ""
#define CHARACTERISTIC_UUID_TX ""
#define VS D10

//vibration sensor
const int vs = D10;
int Sensor_State = 1;

// V S
String cycleBuffer = "";
bool cycleInProgress = false;

//data
void initFileSystem() {
  if (SPIFFS.begin(true)) {
    fileSystemInitialized = true;
    Serial.println("File system initialized");
  }
}

String dataBuffer = "";

// bluetooth
class MyServerCallbacks : public BLEServerCallbacks {
  void onConnect(BLEServer* pServer) {
    deviceConnected = true;
    if (dataBuffer.length() > 0) {
      pTxCharacteristic->setValue(dataBuffer.c_str());
      pTxCharacteristic->notify();
    }
  };

  void onDisconnect(BLEServer* pServer) {
    deviceConnected = false;
  }
};

// data
class MyCallbacks : public BLECharacteristicCallbacks {
  void onWrite(BLECharacteristic* pCharacteristic) {
    std::string rxValue = pCharacteristic->getValue();
    if (rxValue.length() > 0) {
      if (rxValue == "RQD") {
        sendStoredData();
      } else if (rxValue == "CLD") {
        if (fileSystemInitialized) {
          SPIFFS.remove(DATA_FILE);
        }
      }
    }
  }
};

// V S
String getFormattedTimestamp() {
  struct tm timeinfo;
  if (!getLocalTime(&timeinfo)) {
    return "(0000-00-00 00:00:00)";
  }
  char timeStringBuff[25];
  strftime(timeStringBuff, sizeof(timeStringBuff), "%Y-%m-%d %H:%M:%S", &timeinfo);
  return String(timeStringBuff);
}

void setupWiFi() {
  WiFi.mode(WIFI_STA);
  WiFi.begin(ssid, password);

  Serial.print("Connecting to WiFi");
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }

  Serial.println("");
  Serial.println("WiFi connected!");
  Serial.print("IP address: ");
  Serial.println(WiFi.localIP());
  Serial.print("Signal strength (RSSI): ");
  Serial.println(WiFi.RSSI());
}


//v s
void logData(const char* event, long measurement) {
  String dataString;

  if (String(event) == "PRESS 10 STARTED") {
    dataString = "\"" + String(event) + "\", " + getFormattedTimestamp();
    cycleInProgress = true;
    cycleBuffer = dataString;
  } else if (String(event) == "PRESS 10 STOPPED") {
    dataString = "," + getFormattedTimestamp() + ", \"Comment, comment\"" + "\n";
    cycleInProgress = false;
    cycleBuffer += dataString;

    // data
    if (fileSystemInitialized) {
      File dataFile = SPIFFS.open(DATA_FILE, FILE_APPEND);
      if (dataFile) {
        dataFile.print(cycleBuffer);
        dataFile.close();
      }
    }

    //v s
    if (deviceConnected) {
      pTxCharacteristic->setValue(cycleBuffer.c_str());
      pTxCharacteristic->notify();
    } else {
      dataBuffer += cycleBuffer;
    }
    cycleBuffer = "";
  }
}

//data
void sendStoredData() {
  if (fileSystemInitialized && deviceConnected) {
    File dataFile = SPIFFS.open(DATA_FILE, FILE_READ);
    if (dataFile) {

      String fileContent = dataFile.readString();

      pTxCharacteristic->setValue(fileContent.c_str());
      pTxCharacteristic->notify();

      Serial.println("Sending data:");
      Serial.println(fileContent);

      dataFile.close();
    } else {
      String errorMsg = "No data available\n";
      pTxCharacteristic->setValue(errorMsg.c_str());
      pTxCharacteristic->notify();
      Serial.println("Failed to open file");
    }
  } else {
    Serial.println("File system not initialized or device not connected");
  }
}

//vibration sensor
long vibration() {
  long measurement = pulseIn(vs, HIGH);
  return measurement;
}

void setup() {
  pinMode(VS, INPUT);
  Serial.begin(115200);
  setupWiFi();

  //bluetooth
  BLEDevice::init("PRESS 10");
  pServer = BLEDevice::createServer();
  pServer->setCallbacks(new MyServerCallbacks());
  BLEService* pService = pServer->createService(SERVICE_UUID);

  pTxCharacteristic = pService->createCharacteristic(
    CHARACTERISTIC_UUID_TX,
    BLECharacteristic::PROPERTY_NOTIFY);
  pTxCharacteristic->addDescriptor(new BLE2902());

  BLECharacteristic* pRxCharacteristic = pService->createCharacteristic(
    CHARACTERISTIC_UUID_RX,
    BLECharacteristic::PROPERTY_WRITE);

  pRxCharacteristic->setCallbacks(new MyCallbacks());
  pService->start();
  pServer->getAdvertising()->start();
  Serial.println("Waiting for client connection...");

  configTime(gmtOffset_sec, daylightOffset_sec, ntpServer);

  // data
  initFileSystem();
}


void loop() {
  Serial.print(getFormattedTimestamp());
  Serial.print(" - ");

  if (WiFi.status() == WL_CONNECTED) {
    Serial.println("WiFi: Connected | RSSI: " + String(WiFi.RSSI()));
  } else {
    Serial.println("WiFi: Reconnecting...");
    WiFi.reconnect();
  }

  long measurement = vibration();
  Serial.print("Vibration measurement: ");
  Serial.println(measurement);

  if (measurement > 200 && !pressInProgress) {
    Serial.println("EVENT: PRESS 10 STARTED");
    logData("PRESS 10 STARTED", measurement);
    pressInProgress = true;
  } else if (measurement < 1 && pressInProgress) {
    Serial.println("EVENT: PRESS 10 STOPPED");
    logData("PRESS 10 STOPPED", measurement);
    pressInProgress = false;
  }

  delay(5000);
}

This sounds rather like you want to save data to an SD card and download it at leisure later. The datalogger and dumpfile examples in the SD library should be all you need. Since you already use a clock, you can identify the files by timestamp.

Ah okay, I was trying to make this project as cheap as possible but that was where my thoughts were headed too. Thank you for the reply.

I'm not sure what the financial restrictions might be - we are probably talking about $3 of hardware here. Since you are probably using an ESP of some sort, you might have little enough data and sufficient surplus memory to store a one-dimensional array for $0.00, but that brings its own risks.

It's a project for multiple machines so they add up pretty quick :grin: Thanks for the help.