Can't open/locate csv file

Hi, I am fairly new to all this. so sorry if its a straight forward thing. I have tried googling and searching the forum but can’t find the answer anywhere.

What it is I had a script which would calculate time and present it as sensors using persons location i changed this so it uses a csv file to read the times from the csv file however no matter what I do it gives me an error of

  File "/config/custom_components/sensors_athan/sensor.py", line 23, in <module>
    with open('/local/azan_times.csv') as file:
FileNotFoundError: [Errno 2] No such file or directory: '/local/azan_times.csv'

I have included the csv file in the www folder aswell as the same folder as the custom component for both it give me the no such file or directory.

What am I doing wrong? Any help will be appreciated.

without seeing the script its really hard

Here is the full code

"""Platform to retrieve Islamic prayer times information for Home Assistant."""
from datetime import datetime, timedelta
import logging
import csv
import json

from prayer_times_calculator import PrayerTimesCalculator
import voluptuous as vol

from homeassistant.components.sensor import PLATFORM_SCHEMA
from homeassistant.const import DEVICE_CLASS_TIMESTAMP
import homeassistant.helpers.config_validation as cv
from homeassistant.helpers.entity import Entity
from homeassistant.helpers.event import async_track_point_in_time
import homeassistant.util.dt as dt_util

fajar={}
dhuhr={}
asr={}
maghrib={}
isha={}

with open('/local/azan_times.csv') as file:
    reader = csv.reader(file)

    for row in reader:
        fajar[row[0]] = row[1]
        dhuhr[row[0]] = row[2]
        asr[row[0]] = row[3]
        maghrib[row[0]] = row[4]
        isha[row[0]] = row[5]

_LOGGER = logging.getLogger(__name__)

PRAYER_TIMES_ICON = "mdi:calendar-clock"

SENSOR_TYPES = ["fajar", "sunrise", "dhuhr", "asr", "maghrib", "isha", "midnight"]

CONF_CALC_METHOD = "calculation_method"
CONF_SENSORS = "sensors"

CALC_METHODS = ["karachi", "isna", "mwl", "makkah"]
DEFAULT_CALC_METHOD = "isna"
DEFAULT_SENSORS = ["fajr", "dhuhr", "asr", "maghrib", "isha"]

PLATFORM_SCHEMA = PLATFORM_SCHEMA.extend(
    {
        vol.Optional(CONF_CALC_METHOD, default=DEFAULT_CALC_METHOD): vol.In(
            CALC_METHODS
        ),
        vol.Optional(CONF_SENSORS, default=DEFAULT_SENSORS): vol.All(
            cv.ensure_list, vol.Length(min=1), [vol.In(SENSOR_TYPES)]
        ),
    }
)

async def async_setup_platform(hass, config, async_add_entities, discovery_info=None):

    prayer_times = json.dumps(fajar)
    prayer_times = json.dumps(dhuhr)
    prayer_times = json.dumps(asr)
    prayer_times = json.dumps(maghrib)
    prayer_times = json.dumps(isha)

    sensors = []
    for sensor_type in config[CONF_SENSORS]:
        sensors.append(IslamicPrayerTimeSensor(sensor_type, prayer_times_data))

    async_add_entities(sensors, True)

    # schedule the next update for the sensors
    await schedule_future_update(
        hass, sensors, prayer_times["Midnight"], prayer_times_data
    )


async def schedule_future_update(hass, sensors, midnight_time, prayer_times_data):
    """Schedule future update for sensors.

    Midnight is a calculated time.  The specifics of the calculation
    depends on the method of the prayer time calculation.  This calculated
    midnight is the time at which the time to pray the Isha prayers have
    expired.

    Calculated Midnight: The Islamic midnight.
    Traditional Midnight: 12:00AM

    Update logic for prayer times:

    If the Calculated Midnight is before the traditional midnight then wait
    until the traditional midnight to run the update.  This way the day
    will have changed over and we don't need to do any fancy calculations.

    If the Calculated Midnight is after the traditional midnight, then wait
    until after the calculated Midnight.  We don't want to update the prayer
    times too early or else the timings might be incorrect.

    Example:
    calculated midnight = 11:23PM (before traditional midnight)
    Update time: 12:00AM

    calculated midnight = 1:35AM (after traditional midnight)
    update time: 1:36AM.

    """
    _LOGGER.debug("Scheduling next update for Islamic prayer times")

    now = dt_util.as_local(dt_util.now())
    today = now.date()

    midnight_dt_str = f"{today}::{midnight_time}"
    midnight_dt = datetime.strptime(midnight_dt_str, "%Y-%m-%d::%H:%M")

    if now > dt_util.as_local(midnight_dt):
        _LOGGER.debug(
            "Midnight is after day the changes so schedule update "
            "for after Midnight the next day"
        )

        next_update_at = midnight_dt + timedelta(days=1, minutes=1)
    else:
        _LOGGER.debug(
            "Midnight is before the day changes so schedule update for the "
            "next start of day"
        )

        tomorrow = now + timedelta(days=1)
        next_update_at = dt_util.start_of_local_day(tomorrow)

    _LOGGER.debug("Next update scheduled for: %s", str(next_update_at))

    async def update_sensors(_):
        """Update sensors with new prayer times."""
        # Update prayer times
        prayer_times = prayer_times_data.get_new_prayer_times()

        _LOGGER.debug("New prayer times retrieved.  Updating sensors.")

        # Update all prayer times sensors
        for sensor in sensors:
            sensor.async_schedule_update_ha_state(True)

        # Schedule next update
        await schedule_future_update(
            hass, sensors, prayer_times["Midnight"], prayer_times_data
        )

    async_track_point_in_time(hass, update_sensors, next_update_at)


class IslamicPrayerTimesData:
    """Data object for Islamic prayer times."""

    def __init__(self, latitude, longitude, calc_method):
        """Create object to hold data."""
        self.latitude = latitude
        self.longitude = longitude
        self.calc_method = calc_method
        self.prayer_times_info = None

    def get_new_prayer_times(self):
        """Fetch prayer times for today."""

        today = datetime.today().strftime("%Y-%m-%d")

        calc = PrayerTimesCalculator(
            latitude=self.latitude,
            longitude=self.longitude,
            calculation_method=self.calc_method,
            date=str(today),
        )

        self.prayer_times_info = calc.fetch_prayer_times()
        return self.prayer_times_info


class IslamicPrayerTimeSensor(Entity):
    """Representation of an Islamic prayer time sensor."""

    def __init__(self, sensor_type, prayer_times_data):
        """Initialize the Islamic prayer time sensor."""
        self.sensor_type = sensor_type
        self.entity_id = f"sensor.islamic_prayer_time_{self.sensor_type}"
        self.prayer_times_data = prayer_times_data
        self._name = self.sensor_type.capitalize()
        self._device_class = DEVICE_CLASS_TIMESTAMP
        prayer_time = self.prayer_times_data.prayer_times_info[self._name]
        pt_dt = self.get_prayer_time_as_dt(prayer_time)
        self._state = pt_dt.isoformat()

    @property
    def name(self):
        """Return the name of the sensor."""
        return self._name

    @property
    def icon(self):
        """Icon to display in the front end."""
        return PRAYER_TIMES_ICON

    @property
    def state(self):
        """Return the state of the sensor."""
        return self._state

    @property
    def should_poll(self):
        """Disable polling."""
        return False

    @property
    def device_class(self):
        """Return the device class."""
        return self._device_class

    @staticmethod
    def get_prayer_time_as_dt(prayer_time):
        """Create a datetime object for the respective prayer time."""
        today = datetime.today().strftime("%Y-%m-%d")
        date_time_str = f"{today} {prayer_time}"
        pt_dt = dt_util.parse_datetime(date_time_str)
        return pt_dt

    async def async_update(self):
        """Update the sensor."""
        prayer_time = self.prayer_times_data.prayer_times_info[self.name]
        pt_dt = self.get_prayer_time_as_dt(prayer_time)
        self._state = pt_dt.isoformat()

there it is:

change it to:
with open(/config/custom_components/sensors_athan/azan_times.csv’) as file:

and move the csv into your custom_components/sensors_athan folder or whereever you like.

Thanks For your reply and help that worked great, many thanks.

Thanks for helping me figure out where I went wrong. I was wondering if you or if anyone else is kind enough to show me what I have done wrong with the code. First set of code is the original Home assistant platform that calculates times of prayers using latitude and longitude and presents them as sensors.

I have changed the code so instead of using location it uses a CSV with set times and reads from there and presents them as senors. Its all fine but doesnt present the prayer times as sensors.

Any help will be appreciated.

Original Prayer Time Component

Below is my end code after changes to code but it doesn’t output the sensors.

"""Platform to retrieve Islamic prayer times information for Home Assistant."""
from datetime import datetime, timedelta
import logging
import csv
import json

from prayer_times_calculator import PrayerTimesCalculator
import voluptuous as vol

from homeassistant.components.sensor import PLATFORM_SCHEMA
from homeassistant.const import DEVICE_CLASS_TIMESTAMP
import homeassistant.helpers.config_validation as cv
from homeassistant.helpers.entity import Entity
from homeassistant.helpers.event import async_track_point_in_time
import homeassistant.util.dt as dt_util

fajar={}
dhuhr={}
asr={}
maghrib={}
isha={}

with open('/config/custom_components/sensors_athan/azan_times.csv') as file:
    reader = csv.reader(file)

    for row in reader:
        fajar[row[0]] = row[1]
        dhuhr[row[0]] = row[2]
        asr[row[0]] = row[3]
        maghrib[row[0]] = row[4]
        isha[row[0]] = row[5]

_LOGGER = logging.getLogger(__name__)

PRAYER_TIMES_ICON = "mdi:calendar-clock"

SENSOR_TYPES = ["fajar", "sunrise", "dhuhr", "asr", "maghrib", "isha", "midnight"]

CONF_CALC_METHOD = "calculation_method"
CONF_SENSORS = "sensors"

CALC_METHODS = ["karachi", "isna", "mwl", "makkah"]
DEFAULT_CALC_METHOD = "isna"
DEFAULT_SENSORS = ["fajar", "dhuhr", "asr", "maghrib", "isha"]

PLATFORM_SCHEMA = PLATFORM_SCHEMA.extend(
    {
        vol.Optional(CONF_CALC_METHOD, default=DEFAULT_CALC_METHOD): vol.In(
            CALC_METHODS
        ),
        vol.Optional(CONF_SENSORS, default=DEFAULT_SENSORS): vol.All(
            cv.ensure_list, vol.Length(min=1), [vol.In(SENSOR_TYPES)]
        ),
    }
)

async def async_setup_platform(hass, config, async_add_entities, discovery_info=None):

    prayer_times = json.dumps(fajar)
    prayer_times = json.dumps(dhuhr)
    prayer_times = json.dumps(asr)
    prayer_times = json.dumps(maghrib)
    prayer_times = json.dumps(isha)

    sensors = []
    for sensor_type in config[CONF_SENSORS]:
        sensors.append(IslamicPrayerTimeSensor(sensor_type, prayer_times_data))

    async_add_entities(sensors, True)

    # schedule the next update for the sensors
    await schedule_future_update(
        hass, sensors, prayer_times["Midnight"], prayer_times_data
    )


async def schedule_future_update(hass, sensors, midnight_time, prayer_times_data):
    """Schedule future update for sensors.

    Midnight is a calculated time.  The specifics of the calculation
    depends on the method of the prayer time calculation.  This calculated
    midnight is the time at which the time to pray the Isha prayers have
    expired.

    Calculated Midnight: The Islamic midnight.
    Traditional Midnight: 12:00AM

    Update logic for prayer times:

    If the Calculated Midnight is before the traditional midnight then wait
    until the traditional midnight to run the update.  This way the day
    will have changed over and we don't need to do any fancy calculations.

    If the Calculated Midnight is after the traditional midnight, then wait
    until after the calculated Midnight.  We don't want to update the prayer
    times too early or else the timings might be incorrect.

    Example:
    calculated midnight = 11:23PM (before traditional midnight)
    Update time: 12:00AM

    calculated midnight = 1:35AM (after traditional midnight)
    update time: 1:36AM.

    """
    _LOGGER.debug("Scheduling next update for Islamic prayer times")

    now = dt_util.as_local(dt_util.now())
    today = now.date()

    midnight_dt_str = f"{today}::{midnight_time}"
    midnight_dt = datetime.strptime(midnight_dt_str, "%Y-%m-%d::%H:%M")

    if now > dt_util.as_local(midnight_dt):
        _LOGGER.debug(
            "Midnight is after day the changes so schedule update "
            "for after Midnight the next day"
        )

        next_update_at = midnight_dt + timedelta(days=1, minutes=1)
    else:
        _LOGGER.debug(
            "Midnight is before the day changes so schedule update for the "
            "next start of day"
        )

        tomorrow = now + timedelta(days=1)
        next_update_at = dt_util.start_of_local_day(tomorrow)

    _LOGGER.debug("Next update scheduled for: %s", str(next_update_at))

    async def update_sensors(_):
        """Update sensors with new prayer times."""
        # Update prayer times
        prayer_times = prayer_times_data.get_new_prayer_times()

        _LOGGER.debug("New prayer times retrieved.  Updating sensors.")

        # Update all prayer times sensors
        for sensor in sensors:
            sensor.async_schedule_update_ha_state(True)

        # Schedule next update
        await schedule_future_update(
            hass, sensors, prayer_times["Midnight"], prayer_times_data
        )

    async_track_point_in_time(hass, update_sensors, next_update_at)


class IslamicPrayerTimesData:
    """Data object for Islamic prayer times."""

    def __init__(self, latitude, longitude, calc_method):
        """Create object to hold data."""
        self.latitude = latitude
        self.longitude = longitude
        self.calc_method = calc_method
        self.prayer_times_info = None

    def get_new_prayer_times(self):
        """Fetch prayer times for today."""

        today = datetime.today().strftime("%Y-%m-%d")

        calc = PrayerTimesCalculator(
            latitude=self.latitude,
            longitude=self.longitude,
            calculation_method=self.calc_method,
            date=str(today),
        )

        self.prayer_times_info = calc.fetch_prayer_times()
        return self.prayer_times_info


class IslamicPrayerTimeSensor(Entity):
    """Representation of an Islamic prayer time sensor."""

    def __init__(self, sensor_type, prayer_times_data):
        """Initialize the Islamic prayer time sensor."""
        self.sensor_type = sensor_type
        self.entity_id = f"sensor.islamic_prayer_time_{self.sensor_type}"
        self.prayer_times_data = prayer_times_data
        self._name = self.sensor_type.capitalize()
        self._device_class = DEVICE_CLASS_TIMESTAMP
        prayer_time = self.prayer_times_data.prayer_times_info[self._name]
        pt_dt = self.get_prayer_time_as_dt(prayer_time)
        self._state = pt_dt.isoformat()

    @property
    def name(self):
        """Return the name of the sensor."""
        return self._name

    @property
    def icon(self):
        """Icon to display in the front end."""
        return PRAYER_TIMES_ICON

    @property
    def state(self):
        """Return the state of the sensor."""
        return self._state

    @property
    def should_poll(self):
        """Disable polling."""
        return False

    @property
    def device_class(self):
        """Return the device class."""
        return self._device_class

    @staticmethod
    def get_prayer_time_as_dt(prayer_time):
        """Create a datetime object for the respective prayer time."""
        today = datetime.today().strftime("%Y-%m-%d")
        date_time_str = f"{today} {prayer_time}"
        pt_dt = dt_util.parse_datetime(date_time_str)
        return pt_dt

    async def async_update(self):
        """Update the sensor."""
        prayer_time = self.prayer_times_data.prayer_times_info[self.name]
        pt_dt = self.get_prayer_time_as_dt(prayer_time)
        self._state = pt_dt.isoformat()