Giter Club home page Giter Club logo

Comments (118)

Rimco avatar Rimco commented on August 20, 2024 1

Although that might seem a good starting point, all schedules seem to be independent. In our case, we need to be able to combine them intelligently and also predict when they will run. During my conversation with Dan, I also told him I already started implementing such a scheduler before I discovered a Python OSPi existed. Let me copy-paste what I told him:

I've also got some designs lying around and I started coding the basics of the back-end. It contained the scheduler similar to what I described earlier. I designed the program as follows:

First you have "Schedules". Schedules are defined by specifying the active periods. Schedules can optionally repeat after a certain period (1 day, 1 week, 2 weeks, anything). The scheduler can report the time intervals it want to be active given a date/time range. It can also calculate if it would be active at a given moment in time.
In a "Program", you can assign a schedule to each output. So multiple outputs can share the same schedule or they can be completely different. The system can have an arbitrary number of programs. (The current OSPy is a specific case of this in which all outputs use the same schedule.)
Finally, there is one main "Scheduler". This scheduler maintains a list of programs and it can calculate the combined schedule (taking (weather) adjustments and enabled programs into consideration). In addition, each output should have a "usage" property. This usage property (for sprinklers this could indicate pressure drop or flow) will be used by the scheduler to make sure it will never exceed a set "maximum usage". Thereby the user can enforce sequential programs, but it can also be more intelligent by enabling outputs with low usage at the same time. The scheduler tries to execute each schedule as soon as possible without "breaking the rules". Although finding an optimal schedule is a computational hard problem, it is not necessary to find the "optimal" schedule as long as it provides decent results that the user expects. (E.g. by swapping queued schedules you might be able to combine even more outputs and decrease the total running time.)

I have working implementations of these three parts lying around which I could just copy-paste in the current implementation. My main concern is that this would change the behavior significantly making it incompatible with the arduino implementation (for the mobile app).

from ospy.

Rimco avatar Rimco commented on August 20, 2024

About the new API. I know that the mobile app wants to support the arduino based version, but I don't want to let that stop us from improving the python version. The current port is largely based on the arduino code. Although this keeps stuff compatible, it is very non-Pythonic. I've already talked to @Dan-in-CA about this. Let me copy some parts of my conversation:

If I look at the program from a high level, I would expect something like the following:

  • Some output class (such that it can be subclassed to support different hardware implementation). This class should provide a simple interface to set/get outputs. The software that calls these function shouldn't be bothered by the hardware differences.
  • Some logger module that provides simple (standardized) logging facilities. This should take care of the underlying format for storage. Again, other parts of the software shouldn't be bothered by that. It might even support multiple log levels for debug logging and such. It should not be only for schedules but should support an arbitrary format as well.
  • Schedules/programs should also be implemented in some more intelligent classes. These classes should then provide functions to change them and request the resulting schedule. Some "scheduler" class should then use all separate schedules to calculate a complete schedule. This also provides better ways to predict the schedule instead of brute-forcing over all know programs for a given period. This should also solve the "problem" that schedules are ignored if another one is still running instead of being queued. (I personally think this is a real problem.)
  • By doing this re-factoring, the timing loop will be much simpler and the front end (app/webpage) should be able to just ask the scheduler what will be ran during a given period instead of calculating it again.

On the short term I think I will improve the output layer to make it more abstract and be able to use a "dummy" output that can be used during development. Currently all try catch constructions are a bit tricky. Next I want to have a look at the plug-in system. I'd like to be able to enable and disable plug-ins from the GUI and get rid of the executable bits. The executable bits now also influence the system update plugin because it has to ignore them to prevent conflicts.

from ospy.

salbahra avatar salbahra commented on August 20, 2024

It is a very fair point and in the end, so long a plugin can expose the data in the method the app understands, things will work fine. So I agree, don't let the mobile app hold you back.

By the way, some of the issues you mentioned are addressed in firmware 2.1 for Arduino.

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

hello,
a) I have a question it would be possible to add something like a watchdog for plugins. If for some reason the plugin crashes and shuts tried by the ospy him again after some time, run, or send an email about a fall or problem
b) happens to me quite often that after the update I set the time zone setting OSPy to -12 h and master station is turned off (other settings remain)
c) If you are upgrading ospy update using the plugin, I am redirected to the home, but for load changes must reboot the system to load changes
thanks

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Implementing what I've proposed in terms of API only makes sense if there
will be a client for this. So if you are not that interested in supporting
a new API, despite IMHO way better than the current one, there's not much
point in implementing it on the OSP[y|i] side.

Let's first see just how much traction my proposal gets with the community
:)

On Sat, Sep 20, 2014 at 8:01 PM, Martin Pihrt [email protected]
wrote:

hello,
a) I have a question it would be possible to add something like a watchdog
for plugins. If for some reason the plugin crashes and shuts tried by the
ospy him again after some time, run, or send an email about a fall or
problem
b) happens to me quite often that after the update I set the time zone
setting OSPy to -12 h and master station is turned off (other settings
remain)
c) If you are upgrading ospy update using the plugin, I am redirected to
the home, but for load changes must reboot the system to load changes
thanks


Reply to this email directly or view it on GitHub
#24 (comment).

from ospy.

Rimco avatar Rimco commented on August 20, 2024

@martin:
a) This might be part of improving the plug-in system.
b) If this is a real bug that can be reproduced, you can make an issue for it:)
c) The latest System update plugin should do that for you. Although it only works if you use the OSPy service. Do you use that (service ospy start etc.)? Otherwise it might not do that for you. I could make it more robust for these kind of situations.

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

I use a service ospy ... despite the fact I have to manually apply the settings tab reboot the system to load changes. I have a pure clone of https://github.com/Rimco/OSPy and update doing locally (or via sms and click update)

from ospy.

Rimco avatar Rimco commented on August 20, 2024

That's weird, I also have a plain OSPy clone running and updating (using webpage) works fine. It starts updating, initiates a service ospy restart and lets the client wait for the page to come back. In less than 30 seconds I get a new plug-in page telling me the program is up-to-date. I've created a new branch in which I'll try to improve the overal structure (without impacting the api yet). I'll also include extra logging facilities to be able to debug these kind of problems more easily.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

@Rimco - re logging, I'd strongly support using this. As good as they get.
And another, architectural idea, we can have one logger per plugin and one "system logger".

from ospy.

Rimco avatar Rimco commented on August 20, 2024

That's indeed what I would use and my architectural idea is the same. The system should provide some global logging facility that can also be used by plug-ins. This logging facility should also be able to return the entries per group such that plug-ins can use it as feedback for the user.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

@Rimco @salbahra : wiki page with API proposal updated. Added programs data format.

from ospy.

salbahra avatar salbahra commented on August 20, 2024

@teodoryantcheff it's almost like you are using my read_program function as the bases 👍 But really thats exactly what my function does and having the firmware do it is obviously a huge help and lowers the barriers to future development. I love what this is shaping up to be. Also, as Dan mentioned, we should get Jonathan in on this conversation since it sounds like he has already started with the development of it.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

@salbahra - You javascript guys really amaze me! I do understand the language itself, DOM, CSS, HTML5 and all related stuff, but still the way you manage to make it all work together seems like dark-black magic to me. High-five to that !
And haven't looked into your code, actually the whole data structure in programs I "designed" just by looking at the edit program page in the native gui of ospy latest.

from ospy.

salbahra avatar salbahra commented on August 20, 2024

@teodoryantcheff Well I am learning as I go but it's a lot of fun!

I figured, I was just kidding and only meant it abstracts away a lot of the complicated stuff so the UI can focus on it's purpose. The API is essentially only used by the mobile app now and I already have a good idea if you are willing to incorporate it into your proposed API.

Right now, I only support my own plugin in the mobile app. However, if the API allowed, I would be able to manage them in the app and also interact with them (using some sort of agreed format for page formatting). Since I am using jQuery mobile, you could pass a title string and a page content string?

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

@salbahra then you'll like the newly added /plugins/ section :) Very, very raw still, and of course this whole project is a team effort, so whatever is on your mind I want to hear and discuss.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

@Rimco - regarding the scheduler - this seems interesting.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Hi guys,

Please let me know what you think of https://github.com/Rimco/OSPy/blob/refactor/options.py and https://github.com/Rimco/OSPy/blob/refactor/stations.py.

The options instance (from options import options) provides a simple way to get and set options. The predefined options are used for the core functionality. In addition, any object can be saved by giving it to the save function. A similar load function is also available. I think I'm also going to provide some "on change" callback mechanism to notify parts that are interested in a certain property.

You can also use the options instance to save any data persistently. The class makes sure that it will be available whenever the system is restarted. options.test123 = 5 will just work magically;)

Next, the stations implementation makes use of this to magically save station properties. These stations can be used as output instances directly. first_output = stations.get(0) ... first_output.activated = True will do everything for you to enable an output for example.

Let me know what you think, I'm currently trying to figure out which parts that need to be updated to let them work with these new constructions. That seems to be many.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Re your first post and the scheduler - The idea that I have -- say we have a program P that states running valve 2 (station 2) for 2 hours starting 15:00 o'clock every day. So the implementation is :

  • schedule a run operation for 15:00, probably also stating stations.
  • at 15:00 the scheduler invokes a function that enables/starts the affected valves -- this is the on part. And then schedules an off program for 2 hours later.
  • at 17:00, 2 hours later, the scheduler invokes, as previously set by the on part, a function that stops affected valves (calls the off part) and depending on what P is configured to be, sets the next on run.

You can see that this architecture is flexible enough to allow all current kinds of scheduling and some additional ones - seasonal schedules, every friday the 13th, "birthday" watering and so on :) . Also the "next" watering cycle is always known. And schedules visualization remains, just as now, an exercise for the UI. Which is where it belongs in my view.
In a way that is a view on schedule execution from the perspective of a linked list rather than the perspective of an array.
BTW, your view on scheduling as solving for minimal time and not exceeding a certain flow volume is very interesting. Especially the flow limit part. Thanks for sharing !

Finally, as long as the UI can get the same API from the controller, it does make no difference. What I was thinking about this is that the current API (current json API, urls, endpoints and so on) can be implemented as a "legacy" API on top of whatever new we decide to do in ospy.

Will be looking at the new goodies you put up for review shortly, as I have a kid on my hands that needs attention as well :)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Ok, comments here since I couldn't find a way to comment code in-line.

options.py
  • I'd make the init like
    def __init__(self):
        self._values = {}
        self._write_timer = None

        for info in self.OPTIONS:
            self._values[info["key"]] = info["default"]

        with open('./data/options.json', 'r') as options_file:  # A config file
            self._values.update(json.load(options_file))
  • __getattr__ and __setattr__ -- since these only get called when the attribute is not found I think that all the conditionals there can be replaced by
def __getattr__(self, item):
    return self._values[item]

since all other case are implicitly taken care of already... i think.

  • I'd extract the file name to file level or class level "constant"
  • get_categories :
def get_categories(self):
    return sorted(list(set([o.get('category', '') for o in self.OPTIONS])))
  • The Timer idea is el' genial !
stations.py
  • I'd rename activated to simply active everywhere
  • why do you replicate station status to BaseStations.self_state ?
  • activate() and deactivate() to simpler on() and off() in BaseStations ?

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Your json loading seems nicer indeed, I've updated it.

The getattr should indeed only be called if it is not found, but the first self._values = {} seems to call it already. I tried to do what you say, but I found out that this way we are certain we can't get in any race condition. Furthermore, we prevent saving any internal variable by accident.

The setattr is always called, so that certainly needs this construction.

I don't know what you mean with "I'd extract the file name to file level or class level "constant"", please elaborate.

Your get_categories throws away the order and also makes a "" category. If an option has no category, it should not be displayed (automatically) on the options page. And the order specified in the options list should be returned as-is. I like one-liners, but this one seems not to achieve the goal I had in mind;)

I've renamed activated to active, but activate and deactivate seem more logical than on and off to me. I "activate" station 1, I don't "on" station 1. The BaseStation state is not a duplication, it's even the only place where the states are saved. The Station instances query the Stations "factory" what their state is. Why? Because a single station might not be responsible for the state handling. Furthermore, by delegating this question to the proper Stations instance, you could also let it query the real output state instead of some buffered state. At the moment I handle this in the BaseStations to keep the subclasses very simple, they only have to make sure that the self._state is used to set the outputs.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Thanks :)
Re naming -- to put "./data/options.json" as a field or module "constant", but it's a minor thing.
setattr -- brainfart on my side....
Didn't know that order is of use, sorry for not asking first.
Thanks for the explanation of the design as well and ageed on on/off !

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I've made the filepath a constant:) The order was something I didn't think about either in the first place, no problem;)

@salbahra Do you mean to push OSPy to OSPi or to push the refactor branch to master?

from ospy.

salbahra avatar salbahra commented on August 20, 2024

I actually deleted the comment since its technically not development topic but to OSPi since that's the repo people are using.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

General ideas are also welcome here;) We should check if the OSPi branch has some functionality we need to port. I think Dan kept it fairly in sync. If possible, we might ask Dan to update OSPi with our contents. Currently he is referring developers to this version.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Speaking of users -- any idea how big is the userbase of OSPi/y and the arduino variant ?
Also what are you guys watering with ospy/i ? I personally have a lawn (3 sets of sprinklers), some vegetables, some thuia trees and some flowers. Overall ~10 "stations" in ospi lingo.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Oh, and @Rimco 's changes are quite significant and affecting all of the source. I'd be doing logging otherwise or new API. Now I will have to wait :)

from ospy.

Rimco avatar Rimco commented on August 20, 2024

That's why I'm making my changes in a separate branch. You can use the master branch to make your changes;) Although I may change a lot of things, I'm trying to make it as simple as possible. In the end I could get your parts from master and make them work in the refactor branch.

from ospy.

salbahra avatar salbahra commented on August 20, 2024

@teodoryantcheff Addressing your question of how many user's, I can give you some estimates. Roughly 1k OSPi devices are out in use and I assume a large majority of those users are on Dan's OSPi. I think Github does traffic statistics so maybe Dan can give better insight to the software usage.

The other's use Richard Zimmerman's sprinklers_pi app: http://github.com/rszimm/sprinklers_pi or some self-made solution

from ospy.

Rimco avatar Rimco commented on August 20, 2024

@salbahra you just linked to Rays version with new scheduling options, do you have some concrete information? I couldn't find it. If we know what will be the possibilities, we bight be able to stay a bit in sync.

from ospy.

salbahra avatar salbahra commented on August 20, 2024

Sorry I realized the repo itself isn't very helpful. Try this: https://github.com/OpenSprinkler/OpenSprinklerGen2/blob/master/examples/interval_program/interval_program.ino

from ospy.

Rimco avatar Rimco commented on August 20, 2024

btw @teodoryantcheff, we use it mostly for grass, 4 groups for 300 m^2 in total.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I've ported my scheduler proof of concept into my branch. It is adjusted to keep it more similar to the current schedule vs program vs outputs design. Have a look at the program and scheduler files:) I think the following example can make things clear:

With one program:

'Program0': { 'enabled': True,
              'manual': False,
              'modulo': 1440,
              'name': 'Program 01',
              'schedule': [[30, 50]],
              'start': datetime.datetime(2014, 9, 21, 0, 0),
              'stations': [0, 1]}

>>> start = datetime.datetime.combine(datetime.date.today(), datetime.time.min)
>>> end = datetime.datetime.combine(datetime.date.today(), datetime.time.max)
>>> scheduler.combined_schedule(start,end)
{0: [[datetime.datetime(2014, 9, 21, 0, 30), datetime.datetime(2014, 9, 21, 0, 50)]], 
 1: [[datetime.datetime(2014, 9, 21, 0, 50), datetime.datetime(2014, 9, 21, 1, 10)]]}

After changing the modulo to 360:

>>> scheduler.combined_schedule(start, end)
{0: [[datetime.datetime(2014, 9, 21, 0, 30), datetime.datetime(2014, 9, 21, 0, 50)], 
     [datetime.datetime(2014, 9, 21, 6, 30), datetime.datetime(2014, 9, 21, 6, 50)], 
     [datetime.datetime(2014, 9, 21, 12, 30), datetime.datetime(2014, 9, 21, 12, 50)], 
     [datetime.datetime(2014, 9, 21, 18, 30), datetime.datetime(2014, 9, 21, 18, 50)]], 
 1: [[datetime.datetime(2014, 9, 21, 0, 50), datetime.datetime(2014, 9, 21, 1, 10)], 
     [datetime.datetime(2014, 9, 21, 6, 50), datetime.datetime(2014, 9, 21, 7, 10)], 
     [datetime.datetime(2014, 9, 21, 12, 50), datetime.datetime(2014, 9, 21, 13, 10)], 
     [datetime.datetime(2014, 9, 21, 18, 50), datetime.datetime(2014, 9, 21, 19, 10)]]
}

Currently, durations can only be given in minutes. Seconds could be added easily, but I didn't get to changing that yet. Also I've simplified the previously mentioned usage to just support sequential mode. (Weather) level adjustments have also been disabled for now in the scheduler.

Furthermore I had to change the options file to a python shelve to support saving the datetime objects without the need to extend the json save/load. If we really need to save it as json we have to enhance it to be able to save these objects.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Guys, thanks for the info.
@Rimco - what is the name of that design pattern you have applied for station - stations and program - programs (the one you explained when I asked about possible "duplication") ?

[EDIT] comment was entered before the above by Rimco.
Also - I've been meaning to ask -- is there any particular reason to have web.py library as part of the source code ?

from ospy.

Rimco avatar Rimco commented on August 20, 2024

@teodoryantcheff It's a sort of factory design pattern:

In object-oriented programming, a factory is an object for creating other objects – formally a factory is simply an object that returns an object from some method call, which is assumed to be "new".[a] More broadly, a subroutine that returns a "new" object may be referred to as a "factory", as in factory method or factory function. This is a basic concept in OOP, and forms the basis for a number of related software design patterns.

I use it to keep track of them more easily and be able to keep them organized. Although I didn't have a particular design pattern up front, I always adjust implementations on-the-fly to keep them as simple as possible. This ended up to be the most elegant/simple solution in this case, but I'm always open to suggestions.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

It's the part that the created objects reference the factory and vice-verse that evaded me. Other than that I know what a factory pattern is :).
Cheers!

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I use that to make the individual objects a bit more intelligent. I'm not sure if it is according to some actual existing pattern;) Certainly making a station "master" should ensure others are not master anymore, that needs help of some more global manager. Same holds for the outputting in shift registers, individual outputs can't do that, the manager can:)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

It's not a factory for sure :)
So regarding web.py being part of the source tree ?
And also, regarding the scheduler -- what is the benefit of knowing all the daily on-off times for a program ?

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Ah, now I see your edit;) I don't know why and I don't know for sure how to get rid of it. We might detect that it's not available and install it automatically. Then we could install it globally or create a some copy in a subdirectory. The last option might interfere with the automatic update system.

Or we could require users to install it as a precondition, but I like to keep it simple for users:)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

OK, will think about it.
What about a __getitem__ override in BaseStation ?

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

And also, regarding the scheduler -- what is the benefit of knowing all the daily on-off times for a program ?

from ospy.

Rimco avatar Rimco commented on August 20, 2024

getitem seems a good idea for Stations, I'll have a look at it.

Knowing the on-off time is already needed in many places: It is calculated in the timing loop, it is calculated client-side in JS and it's calculated in the mobile app. By calculating it in a single location, many parts of the implementation can be simplified.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Just pushed a raw API, working with dummy data since I think the underlying data structures will change with Rimco's upcoming work. Quick review here and here.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

BTW, adding a plugin more complex than one single file is ugly right now, taking this into account maybe a good idea whenever the plugins system gets redone.

from ospy.

Dan-in-CA avatar Dan-in-CA commented on August 20, 2024

Yes. This has been discussed on the forum.
http://rayshobby.net/phpBB3/viewtopic.php?f=28&t=817

You should really take some time to read through the discussions that have taken place over the past year and a half or so.

There is also a documentation wiki that is worth a look:
http://rayshobby.net/mediawiki/index.php?title=Python_Interval_Program_for_OSPi

Users have a wide range of skill levels and interests. It is important to keep any changes as smooth as possible for them.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

@Dan-in-CA - yes, you are absolutely right. I've missed the forum completely. Thanks !

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Hi all,

I think I'm finished with the most crucial parts of the new back-end. Current results:

Stations module that supports RPi, BBB and dummy outputs. Dummy outputs are used as fallback if no other type is available and print info when they are activated. These can be used during debugging to test what would happen.

Station properties:

  • Index (Output #)
  • Name
  • Enabled
  • Ignore Rain
  • Active
  • Activate master
  • Is master

All station instances are managed by a Stations instance with:

  • Fetching instances
  • Changing number of outputs
  • Activate station (can also be done using a station instance)
  • Checking station state(s)
  • Master station (index)
  • Clear outputs function

Programs module providing very flexible programs:

Program properties:

  • Name
  • Enabled
  • Selected stations
  • Schedule (list of intervals in minutes during which the program should be activated)
  • Manual (True/False): Indicates if the program should be repeated or this is a "Run-Once" program. This now also supports adding a Run-Once program planned in the future.
  • Modulo of the schedule (repeat every x minutes/days/weeks)
  • Start date(time) to indicate what should be used as starting point for all calculations

All program instances are managed by a Programs instance with "normal" list operations. These ensure programs stay in sync with the persistent storage.

Options class providing options and more generic persistent storage. This class provides convenience functions to load and save data for arbitrary objects. New members can be added by explicitly defining them or by dynamic creation (for plug-ins). All information needed for the options page is also included.

Log module providing a log instance. This module ensures all python logging is captured whenever debug_log is enabled in the options. This should be used by developers or if problems are investigated. This will also ensure all log entries are saved to a human-readable log file. In addition, the log instance provides functions to log events for arbitrary "event_types". For example, a plug-in can log its events using its own event_type. After that, the plug-in can fetch the log entries of that type to present an overview to the user. If debug logging is disabled, information is logged as-is (minimum log level=INFO). With debug logging enabled extra information is added and the minimum log level is lowered to DEBUG automatically.

Events can be generated in two ways:

import logging #standard python module
logging.info('This could be displayed to the user', extra={event_type='Plugin1'})
logging.debug('This will be visible to the user if debug_log is enabled', extra={event_type='Plugin1'}) 
logging.debug('This will only be visible in the log file if debug_log is enabled') 

from log import log #OSPy log instance
log.log_event('Plugin1', 'This could be displayed to the user')
log.log_event('Plugin1', 'This will be visible to the user if debug_log is enabled', logging.DEBUG)

The first option has the advantage that it can add more information (line numbers etc) during debugging. Porting this functionality to the log instance variant is a TODO.

The scheduler module provides all information that is needed to determine which outputs should be activated according to the schedules. The predicted_schedule returns an overview of runs that are predicted to run during the given time range. The time range can also lie in the past, in which case it will return what should have been run according to the current schedule.

The combined_schedule also takes the current time into account. If we are looking at a point in the past, we should use the information from the log. For the future, we look at the prediction. Additionally, we add the currently active runs if applicable.

The check_schedule function performs the actions that should be done whenever automatic mode is enabled. It looks at the scheduled runs and ensures that the corresponding outputs are enabled. It also ensures that the master output is enabled if needed. The master output now also supports a negative master_on_delay. (Master can be activated before actually opening a "normal" output.)

TODO:

  • Add support for rain sensor/delay
  • Implement some "global" adjustment value
  • Remove code that is now not needed anymore
  • Update all front-end code to use the new back-end
  • Check if there is more to do to support Run-Once programs
  • Check manual mode support (should not need much)

This all should be a complete back-end replacement making the overall program better readable and maintainable. I'm not sure up to what extend it will be compatible with the original front-end / interfaces, but I didn't want to let this refactoring be limited by that. The back-end should support at least the original functionality, except that overlapping programs (E.g. 8:00-8:15 and 8:10-:8:30) will now be scheduled properly instead of just skipping the second entry.

from ospy.

Dan-in-CA avatar Dan-in-CA commented on August 20, 2024

Sounds really interesting.

Is it supposed to be able to run? I get the following error:
NameError: name 'sd' is not defined

from ospy.

Rimco avatar Rimco commented on August 20, 2024

It's not yet supposed to run;) Although the back-end is (somewhat)
complete, the front-end needs an update to make use of it.
I already started removing some old stuff which has certainly broken the
current front-end.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Btw, I tested the back-end by opening a python shell in the OSPy directory.
For example, the following should work:

from options import options
print options
options.debug_log = True

from stations import stations
stations.master = 3
s1 = stations.get(0)
s1.name = 'Output test'
s1.enabled = True
s1.activate_master = True

from programs import programs
programs.add_program()
p1 = programs.get(0)
p1.name = 'New name'
p1.stations = [0]
p1.add(300, 1000)
print p1.schedule

import datetime
current_time = datetime.datetime.now()
check_start = current_time - datetime.timedelta(days=1)
check_end = current_time + datetime.timedelta(days=1)

import scheduler
print scheduler.combined_schedule(check_start, check_end)
scheduler.check_schedule()

from ospy.

Dan-in-CA avatar Dan-in-CA commented on August 20, 2024

Cool!
I read through your code and it looks very clean and concise. The code spinets you posted above are very helpful to see what it does.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Great work, @Rimco !! Let me know how can I help with making the current source work with the new stuff ?

Unrelated -- bpython is a very cool interpreter, check it out.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I'll have a look at what needs to be done in a couple of hours. I think you
can help by updating pages to use the new structures, those should be
pretty straightforward now:)
Let me know if you start with something such that I don't do it at the same
time;) I still have to update all stuff that tries to use global variables
that have been deleted and I have to check how to switch between auto and
manual mode.

bpython seems pretty cool indeed:)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Oh, mama ... :) Ok, will start with the webpages.
Options are meant to be used just by importing options and using the options variable defined there ?

Also is this by design ? :

In[8]: options.run_log
Out[8]: False
In[10]: options.run_log2
Traceback (most recent call last):
  File "C:\Python27\lib\site-packages\IPython\core\interactiveshell.py", line 2883, in run_code
    exec(code_obj, self.user_global_ns, self.user_ns)
  File "<ipython-input-10-4f8bf7c0144d>", line 1, in <module>
    options.run_log2
  File "C:\.....ts\OSPy\options.py", line 202, in __getattr__
    result = self._values[item]
KeyError: 'run_log2'
In[11]: options.run_log2 = 'fdg'
In[12]: options.run_log2
Out[12]: 'fdg'

I'd assume that users of the Options class are not to be permitted to add arbitrary options.
Finally I see that your preference is for the options to be used in the dot notation. Do you see any merit in adding

    """ Makes possible using this class like options[<item>] """
    __getitem__ = __getattr__

    """ Makes possible using this class like options[<item>] = <value> """
    __setitem__ = __setattr__

to the class definition ?

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Yes. Options should be used like you said. Let me know if you encounter problems with any page in the current set-up.

Btw, I use the "Options" class for everything that needs to be saved persistently. Most entries are indeed options, but also logs and other settings are saved using this class.

Plug-ins are allowed to add new "options" if they need to save some information persistently. I'm still thinking how I can make that nicely such they also have defaults. Currently, you are allowed to use undefined keys as long as you make sure they are set before you get. I'm also thinking if there is still a need to have global variables at all. I think we can avoid them.

If you think having a dictionary interface as well is useful, you can add it;)

I'll have a look at the options page myself. That page should use the information of the options class to show all options dynamically and might need some adjustments in the back-end.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

OK, good. Regarding getting rid of globals -- yes, that's the right thing to do but it ain't gonna be easy... For example gv is sent to each and every web page now, as part of template_globals..
After starting work I got these questions :

  • I think that currently water level is implemented as part of a plugin, but really should be part of the core scheduler. Have you planned for such functionality ? Also there's no notion of water level in the new Options.
  • Rain Delay really means scheduled programming ignore time -- meaning that no programs will be run until now() > rdst ? What is the meaning of sd['rd'] and sd['rdst'] ? Maybe @Dan-in-CA can help me here.
  • There is no option for "Ignore password". Is this intended and if yes, what's the plan ? :)
  • There is a program_count in options. Why ?
  • How is rain sensor to read with the new stations implementation ?

from ospy.

Rimco avatar Rimco commented on August 20, 2024
  • I replaced sending gv with sending options, we might need to add some extra classes like outputs, inputs etc, but you can do that when needed.
  • I didn't have a look at rain delay yet. I fixed the rain delay input, but we might need some "rain_delay_end" option at least. That should be a datetime instance. It can be then set by the user (or a plugin). We could also add some sprinkler_blocks for plugins in the same way as level_adjustments.
  • there is an ignore_password option:
    "key": "no_password",
    "name": "Disable security",
  • program_count was needed because I try to load that number of programs from the database. I might be able to remove it if I just "try" to load as many programs as available in the database. You should not need to access it directly, it should only be used by the Programs class.
  • rain sensor has just been added:) see the inputs module.

from ospy.

Dan-in-CA avatar Dan-in-CA commented on August 20, 2024

All the sd[] values are described in the gv_reference.txt file.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Thank you for your answer.
I know and I checked there as well. Just wanted to be sure what "Rain Delay" means in ospi.

from ospy.

Dan-in-CA avatar Dan-in-CA commented on August 20, 2024

To be more precise, the user enters a length of time for no irrigation to occur. The rdst is calculated as now + length of delay and a countdown is show in the UI

from ospy.

Rimco avatar Rimco commented on August 20, 2024

My latest commit should have added a proper replacement for it:)

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Now we (should) have a home page that works correctly :D The timer readback of manual mode is not yet supported, but it will correctly activate/deactivate the outputs. The time-out you have specified will work anyways.

You can use manual mode to test activating outputs, it will show up in the history if you switch back to automatic mode. Be sure to enable debug logging in the options menu to see what happens if you want to test without HW.

For example:

2014-09-28 01:04:01,000 [START  Run] Program -1 - Station 0: From 2014-09-28 01:04:01 to 2014-09-28 01:04:11
2014-09-28 01:04:01,776 [DEBUG Event] stations.py:161: Activated output 0
127.0.0.1:60550 - - [28/Sep/2014 01:04:01] "HTTP/1.1 GET /sn" - 303 See Other
127.0.0.1:60550 - - [28/Sep/2014 01:04:01] "HTTP/1.1 GET /" - 200 OK
127.0.0.1:60550 - - [28/Sep/2014 01:04:01] "HTTP/1.1 GET /api/log" - 200 OK
2014-09-28 01:04:14,000 [FINISH Run] Program -1 - Station 0: From 2014-09-28 01:04:01 to 2014-09-28 01:04:14
2014-09-28 01:04:14,963 [DEBUG Event] stations.py:165: Deactivated output 0
...
2014-09-28 01:07:24,000 [START  Run] Program -1 - Station 1: From 2014-09-28 01:07:24 to 2024-09-25 01:07:24
2014-09-28 01:07:24,532 [DEBUG Event] stations.py:161: Activated output 1
...
2014-09-28 01:07:56,000 [FINISH Run] Program -1 - Station 1: From 2014-09-28 01:07:24 to 2014-09-28 01:07:56
2014-09-28 01:07:56,375 [DEBUG Event] stations.py:169: Cleared all outputs
127.0.0.1:60809 - - [28/Sep/2014 01:07:56] "HTTP/1.1 GET /" - 200 OK
127.0.0.1:60809 - - [28/Sep/2014 01:07:56] "HTTP/1.1 GET /api/log" - 200 OK
2014-09-28 01:08:02,881 [DEBUG Event] stations.py:169: Cleared all outputs

P.s. I currently use 10 years as "never stop". I think that should be sufficient for now;)

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I've been steadily working on all pages that were not working yet. The latest addition is the support to add and edit programs. Although a created/changed program is not saved yet, the client side is done. I've added more ways to create programs and one I personally like most, is the custom program.

Because my JavaScript knowledge is a bit outdated, feel free to have a look at the implementation and improve it where possible. This also holds for the Python code, although I expect less problems there.

I will now continue working on the saving of the changed programs in the python counterpart. After that, the only "major" thing left is the Run-once page. If this has been done, all (core) functionality should be working again with the new back-end.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

I did check progress yesterday. Amazing stuff !! Cheers !

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Hi guys. Here's a quick update from me -
API is coming together quite nicely. You can take a look on the API branch in my fork. The only major part that is left to be implemented as of now is the programs API. The nice thing is that all the major parts are there already and it's only a matter of sitting down and getting to understand how did @Rimco wire it in OSPy currently. I've left all user auth out for the time being since it's still to be considered a work in progress.... a developers preview if you like :)

Along these same lines I did spend quite some time teaching myself about the brave new (and crazy) world of front-end development. I created an API client in AngularJS. Shared on github here. To be honest and as a kudos to @salbahra I still can't understand how people do code in javascript for a living ... on a daily basis. It's such an insane language that I can't even ...
Anyways, Angular-OSPy is at the stage of not even being a preview. But still I'd love to hear your commens

So to make it all work :

  • checkout the API branch of my ospy fork
  • start it. python ospy.py is enough. It should listen on http://localhost:8080
  • Play around with the API with a REST client like Advanced REST Client in Chrome or whatever your preference is. Note that currently all API URLs are prefixed with /rapi/1.0 since /api was already taken. I know - it's ugly... :)
  • clone the angular-ospy project locally and follow the install instructions from the readme on github

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Nice work:) I was away last week so I'll have a closer look next week. I saw that your latest commit had something to do with local vs GMT. Do you have a clear vision what should be used? Normally I would say everything should be GMT (or epoch) based.

In this case, I can understand that the RPi time should be used including its timezone. If so, clients should know the local time of the RPi or they should know which time zone/offset is used by the RPi. This way, a client can convert times if needed and can also display the current RPi time. I've done this for the clock displayed on the webpage, but it was a bit tricky because JavaScript also expects local times etc.

Btw, I've heard before that AngularJS is nice for this kind of stuff, but I would still refuse to code JS on a daily basis;)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Well, I thought about GMT times as well... and to be honest the reason that I made the API return GMT times is ... the fact that in JavaScript it turns out it's hell to parse an ISO8601 encoded dated in local time. All current implementations (FF, V8...) assume that if the stamp is in 8601 then the date is GMT based. And also it turns out that until very recently even that was considered "platform dependent". Just how cool is that ?! Your were "lucky" that you had the option to provide local time to the Date() instance on the web.py generated page.
OTOH what dates get encoded in is not such a big deal since if you think about it the chance of the user of such a "home" irrigation system needing anything else than local is slim at best.
BTW I noted that logs (ospy logs that is), do get removed pretty fast - within 1-2 minutes of getting into the list. Did not chase this any further, but I think that there may be something fishy with log auto-deletion.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

For dates, I would never send strings to transfer information between 2 machines. Something simple as the epoch time should suffice. If you do that, you can agree if that time is GMT or local time. You could even send both such that a client can do what he wants.
Keeping the local time of the system is a pretty useful feature. For example, during my holiday I was in a different timezone. By displaying the local time of the device and by using the local time for schedules, you won't get confused by a time/schedule that has suddenly changed.
And regarding the logs: Unless logging/debugging is enabled in the options, only the logs that are needed to keep track of what is already done are kept. (Needed to ensure the scheduler knows which intervals to skip.)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Hi. I think the bulk of the API is done. Here's a brief description, as I will update the "proposal" doc in the wiki later on.

Generics

Authentication is supported via HTTP Authorization headers for BASIC auth. Currently actions that make changes need to be authenticated and read-only ones (GETs usually) do not. The "No security" ospy option is respected.
All data is json encoded. Dates are timestamps in seconds since epoch. Note that JavaScript uses milliseconds and values received from opsy need to be multiplied by 1000.
HTTP status codes are properly used and json encoded errors are returned where needed.

There are the following endpoints :

  • Stations
  • Programs
  • Options
  • Logs
  • System

Stations

Doing a GET on /stations returns a response like :

[
{
 "id": 0, 
 "running": false, 
  "remaining_seconds": 0, 
  "name": "station 1", 
  "activate_master": false, 
  "is_master": false, 
  "ignore_rain": false, 
  "enabled": true, 

},
... and so on for all the stations configured
]

You can also do a GET to /stations/1 and get this station's info only.
Stations supports actions as well. Available via a POST (empty body) to /stations/<staton_id>?do=<action>. Supported actions currently are "start" and "stop". So a POST to /stations/1?do=start will start start the station with id 1.
Stations can be edited by using PUT to either /stations for all stations or a particular one with /stations/<id>. Updates are "partial" meaning that not all key value pairs need to be present in the request data. For example PUTting

{"name":"new station name"}

to /stations/3 will rename that station without affecting other station parameters or other stations.

Programs

A GET to /programs :

[{
  "id": 0, 
  "name": "Program 01", 
  "modulo": 10080, 
  "schedule": [[1845, 1900], [4725, 4780], [7605, 7660]], 
  "enabled": true, 
  "stations": [0, 2, 4], 
  "type_name": "DAYS_SIMPLE", 
  "type_data": [405, 55, 30, 0, [1, 3, 5]], 
  "manual": false, 
  "summary": "Simple schedule on Tue Thu Sat", 
  "start": 1415570400, 
  "type": 0
}]

POSTing to /programs creates a new program with the parameters in the POST data. Also posting empty to /programs/<program_id>?do=<action> executes what I call program actions. Currently "runnow" and "stop" are supported.

PUT is for editing programs. Only individual programs can be edited. Again partial updates are supported.

Note that as of now only CUSTOM schedules are properly supported. The thing is that according to me the others are redundant, as CUSTOM can be used to achieve any schedule really and also the most flexible option.

DELETE is supported on both all programs and individual ones deleting either all programs or the selected one respectively.

Options

GET /options gives you

{
  "scheduler_enabled": true,
  "run_entries": 100,
  "rain_sensor_enabled": false,
  "run_log": false,
  "web_port": 8080,
  "name": "Mega ospy server",
  "no_password": true,
  "station_delay": 0,
  "output_count": 8,
  "temp_unit": "C",
  "rain_block": 0,
   "manual_mode": false, 
  "master_on_delay": 0, 
  "sequential": false, 
  "location": "", 
  "debug_log": false, 
  "rain_sensor_no": false, 
  "level_adjustment": 1, 
  "master_off_delay": 0
}

Also GET to /options?annotated=true is supported giving :

{
  "scheduler_enabled": {
    "category": "",
    "name": "Enable scheduler",
    "min": "",
    "default": true,
    "max": "",
    "value": true,
    "help": ""
  },
  "run_entries": {
    "category": "Logging",
    "name": "Max run entries",
    "min": 0,
    "default": 100,
    "max": 1000,
    "value": 100,
    "help": "Number of run entries to save to disk, 0=no limit."
  },
  "rain_sensor_enabled": {
    "category": "Rain Sensor",
    "name": "Use rain sensor",
    "min": "",
    "default": false,
    "max": "",
    "value": false,
    "help": "Use rain sensor."
  },
  "output_count": {
    "category": "Station Handling",
    "name": "Number of outputs",
    "min": 8,
    "default": 8,
    "max": 1000,
    "value": 8,
    "help": "The number of outputs available (8 + 8*extensions)"
  },
  "web_port": {
    "category": "System",
    "name": "HTTP port",
    "min": 1,
    "default": 8080,
    "max": 65535,
    "value": 8080,
    "help": "HTTP port (effective after reboot.)"
  },
  "name": {
    "category": "System",
    "name": "System name",
    "min": "",
    "default": "OpenSprinkler Pi",
    "max": "",
    "value": "Mega ospy server",
    "help": "Unique name of this OpenSprinkler system."
  },
  "no_password": {
    "category": "Security",
    "name": "Disable security",
    "min": "",
    "default": false,
    "max": "",
    "value": true,
    "help": "Allow anonymous users to access the system without a password."
  },
  "station_delay": {
    "category": "Station Handling",
    "name": "Station delay",
    "min": 0,
    "default": 0,
    "max": 3600,
    "value": 0,
    "help": "Station delay time (in seconds), between 0 and 3600."
  },
  "run_log": {
    "category": "Logging",
    "name": "Enable run log",
    "min": "",
    "default": false,
    "max": "",
    "value": false,
    "help": "Log all runs - note that repetitive writing to an SD card can shorten its lifespan."
  },
  "temp_unit": {
    "category": "",
    "name": "C\/F",
    "min": "",
    "default": "C",
    "max": "",
    "value": "C",
    "help": ""
  },
  "rain_block": {
    "category": "",
    "name": "Rain block (rain delay) set by the user (datetime)",
    "min": "",
    "default": -7200,
    "max": "",
    "value": -7200,
    "help": ""
  },
  "manual_mode": {
    "category": "",
    "name": "Manual operation",
    "min": "",
    "default": false,
    "max": "",
    "value": false,
    "help": ""
  },
  "master_on_delay": {
    "category": "Configure Master",
    "name": "Master on delay",
    "min": -1800,
    "default": 0,
    "max": 1800,
    "value": 0,
    "help": "Master on delay (in seconds), between -1800 and +1800."
  },
  "sequential": {
    "category": "Station Handling",
    "name": "Sequential",
    "min": "",
    "default": true,
    "max": "",
    "value": false,
    "help": "Sequential or concurrent running mode."
  },
  "location": {
    "category": "System",
    "name": "Location",
    "min": "",
    "default": "",
    "max": "",
    "value": "",
    "help": "City name or zip code. Use comma or + in place of space."
  },
  "debug_log": {
    "category": "Logging",
    "name": "Enable debug log",
    "min": "",
    "default": false,
    "max": "",
    "value": false,
    "help": "Log all internal events (for debugging purposes)."
  },
  "rain_sensor_no": {
    "category": "Rain Sensor",
    "name": "Normally open",
    "min": "",
    "default": true,
    "max": "",
    "value": false,
    "help": "Rain sensor default."
  },
  "level_adjustment": {
    "category": "",
    "name": "Level adjustment set by the user (fraction)",
    "min": "",
    "default": 1,
    "max": "",
    "value": 1,
    "help": ""
  },
  "master_off_delay": {
    "category": "Configure Master",
    "name": "Master off delay",
    "min": -1800,
    "default": 0,
    "max": 1800,
    "value": 0,
    "help": "Master off delay (in seconds), between -1800 and +1800."
  }
}

which is a useful format for front-end presentation.
POST is not supported. PUT is used to edit options. E.g. PUTting

{
"name": "a new system name"
}

to /options will rename the system.

Logs

GET will return the current log table and DELETE will clear the run log.

System

Supports GET and POST. GET returns

{
"uptime": "0:06:19",
"release_date": "2014-09-28",
"platform": "pi",
"version": "2.2.999",
"CPU_temperature": "45.5",
"rpi_revision": 2
}

POST supports "actions" in the "?do=" notation -- reboot, restart and poweroff, which I think are self-explanatory.


Source code available from the API branch of my fork. @Rimco, please let me know if I should send you a pull request now or wait till you finish with the plugins ? .. if at all :)

Cheers,

Teo

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Nice to see the progress:) I can merge what you have in the refactor branch when you want. In that way we can also prevent having conflicts later on. We can than also ensure we have a complete working version we can push to the master in one go.

I'm currently very busy, but I'll try to do some OSPy work later this week. The basics for the plug-ins are there, but all plug-ins will need some adjustments. My latest commit details the structure a bit:

Started with plug-in system. Implemented dynamic loading. Plug-ins should provide:
NAME, LINK (may be None), URLS.
start and stop method.

See system_update for (an incomplete) example.

The system works without the plug-ins, but they provide some very useful functionality I don't want to break in the master;)

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

wow, great. I have a couple of new plugins and waiting for the new release (refactor with plugins), i am waiting for support plugins. Thank you boys

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

A very ugly, but working solution to the templating problem with the new proposed path structure for plugins is to add a

self.plugin_template_render = web.template.render(os.path.join('templates', 'plugins'), globals=template_globals, base='base')

to webpages.py, use

return self.plugin_template_render.xyz()

in the plugin and have base.html either copied to templates/plugins or symlinked there...
The thing is that I find this very ugly ! But after some looking at the code of web.py and also some googling could not find a decent way to put templates into sub-folders.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

If I remember correctly, I've already fixed it for the system_update
plugin. There was some proper way.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Apparently I didn't do that yet, but I can remember that I found some instructions somewhere. I'll try to find something for which we don't need to duplicate base.html...

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I found it again: https://bugs.launchpad.net/webpy/+bug/224354
This describes a bug, but the example shows how you can use subdirectories easily, by just adding the directory name when you specify the template.

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I've pushed a complete working system_status plugin. This also includes the template trick described before. It also shows how the central logging system can be used for status information.

In addition I also merged the plugin changes into the refactor branch.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

I should have been smarter and look for a fix to the 'base' problem... not 'web.py template subdirectories' :)

👍

Cheers,

Teo

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I found it by searching for "web.py template subdirectory", it was the
third result for me:)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

And the 1st one for me :

image

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Short update...
Done:
Email plug-in: Cleaned-up, working, ready.
LCD display plug-in: Cleaned-up, working, ready.
Monthly water level plug-in: Cleaned-up, working, ready.
Relay plug-in: Very simple, working, ready.
System update plug-in: Cleaned-up, working, ready.
Weather-based water level plug-in: Cleaned-up, working, ready.

TODO:
Pressure sensor plug-in: Not started, needs some clean-up.
SMS plug-in: Not started, needs some clean-up.
UPS plug-in: Not started, needs some clean-up.
Weather based rain delay plug-in: Not started, needs some clean-up.

Mobile app plug-in: Not started, will be difficult if we want to be backwards compatible.
System info plug-in: Works but should be cleaned-up to use new available helpers, it should also not need a separate thread.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Amazing !

On Sat, Nov 22, 2014 at 11:55 PM, Rimco [email protected] wrote:

Short update...
Done:
Email plug-in: Cleaned-up, working, ready.
LCD display plug-in: Cleaned-up, working, ready.
Monthly water level plug-in: Cleaned-up, working, ready.
Relay plug-in: Very simple, working, ready.
System update plug-in: Cleaned-up, working, ready.
Weather-based water level plug-in: Cleaned-up, working, ready.

TODO:
Pressure sensor plug-in: Not started, needs some clean-up.
SMS plug-in: Not started, needs some clean-up.
UPS plug-in: Not started, needs some clean-up.
Weather based rain delay plug-in: Not started, needs some clean-up.

Mobile app plug-in: Not started, will be difficult if we want to be
backwards compatible.
System info plug-in: Works but should be cleaned-up to use new available
helpers, it should also not need a separate thread.


Reply to this email directly or view it on GitHub
#24 (comment).

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

It's very amazing! LCD plugin has very nice code
I see that you know how to programing. I am barbarian in Python :-)

In plugin Weather-based Water Level is error:
Checking weather status...
Weather-based water level plug-in:
Traceback (most recent call last):
File "/home/pi/OSPy/plugins/weather_based_water_level.py", line 75, in run
history = history_info()
File "/home/pi/OSPy/plugins/weather_based_water_level.py", line 247, in history_info
'temp_c': float(day_info['maxtempm']),
ValueError: could not convert string to float:

Thank you Martin

PS.
I have a question:
We will form a plugin that will show debug log file, or it will be part of the page log? that it can be read errors even without direct access from the rear

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

in lcd plugin is error if rain sensor is enabled:
Traceback (most recent call last):
File "/home/pi/OSPy/plugins/lcd_display.py", line 69, in run
line2 = get_report(report_index+1)
File "/home/pi/OSPy/plugins/lcd_display.py", line 161, in get_report
if inputs.rain_sensed():
File "/home/pi/OSPy/inputs.py", line 9, in rain_sensed
return options.rain_sensor_enabled and (options.rain_sensor_no == self.rain_input)
File "/home/pi/OSPy/inputs.py", line 25, in getattr
return self._io.input(self._mapping[item])
RuntimeError: You must setup() the GPIO channel first

from ospy.

Rimco avatar Rimco commented on August 20, 2024

I think I have solved this issue with the latest commit:)

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Hey, just as a side note -- I spent and hour or so and have a semi-working WSGI based ospy. For the interested - c292bb4 .
Essentially it all works, less web pages of plugins (guessing auto-url creation and/or templates) and the fact that apache logs whatever ospy spews into the error log of the web-site. Preliminary testing shows ~2 times faster page load times, but still very slow :)

from ospy.

Rimco avatar Rimco commented on August 20, 2024

To quote yourself:
TODO does wsgi make sense at all ???
In other words: What would be the advantage?

Edit: I should read the whole message before replying, so essentially it would speed things up?

from ospy.

salbahra avatar salbahra commented on August 20, 2024

I think security is the advantage. You can enable SSL and basic
authentication. This is something my app supports as well.

Btw still been following the project here and can't wait for it to wrap up
into a stable version. Absolutely amazing work going on here!

On Friday, December 5, 2014, Rimco [email protected] wrote:

To quote yourself:
TODO does wsgi make sense at all ???
In other words: What would be the advantage?


Reply to this email directly or view it on GitHub
#24 (comment).

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

Hoped to squeeze some page load speed, but other than that -- ssl and not
much more.
Oh, and "production deployment" :P

On Sat, Dec 6, 2014 at 12:24 AM, Samer Albahra [email protected]
wrote:

I think security is the advantage. You can enable SSL and basic
authentication. This is something my app supports as well.

Btw still been following the project here and can't wait for it to wrap up
into a stable version. Absolutely amazing work going on here!

On Friday, December 5, 2014, Rimco [email protected] wrote:

To quote yourself:
TODO does wsgi make sense at all ???
In other words: What would be the advantage?


Reply to this email directly or view it on GitHub
#24 (comment).


Reply to this email directly or view it on GitHub
#24 (comment).

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Fair enough, improvement is improvement. And indeed, SSL would be nice.

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

Hello everyone,
I have a problem with the shift outputs in ospy refactor.
a) if I upload ospy from git (Rimco - master not refactor) everything works - outputs (shift register) ok. if program set station to on - station is set to on. all is ok.
b) if I upload ospy from git (Rimco - refactor) not function any output from shift register

No function any output from shift register. In debug is print:
2014-12-08 12:42:54,650 [START Run] Program 0 - Station 1: From 2014-12-08 12:42:54 to 2014-12-08 12:50:00
2014-12-08 12:42:54,654 [START Run] Program 0 - Station 2: From 2014-12-08 12:42:54 to 2014-12-08 12:50:00
2014-12-08 12:50:01,146 [FINISH Run] Program 0 - Station 1: From 2014-12-08 12:42:54 to 2014-12-08 12:50:01
2014-12-08 12:50:01,150 [DEBUG Event] stations.py:185: Deactivated output 1
2014-12-08 12:50:01,157 [FINISH Run] Program 0 - Station 2: From 2014-12-08 12:42:54 to 2014-12-08 12:50:01
2014-12-08 12:50:01,160 [DEBUG Event] stations.py:185: Deactivated output 2

in debug is all ok, but shift register not function. I have a raspberry pi.
Is it a mistake? or to other boys OSPy works with shift register?

LCD plugin is really now OK, thanks Rimco

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Seems to be an issue, I think it didn't recognize the RPi properly. Please
create an issue on github such that I won't forget to look at it;)

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Finally found some time to look at the issues...

Done:
Fixed all reported issues.
System info plug-in: Cleaned-up, working, ready.

TODO:
Mobile app plug-in: Martin started, but I'm not sure if we'll be ever able to be compatible with the current mobile app. We are now at a point where we have much more functionality and in a completely different format. We might need to consider dropping its support for now.
Pressure sensor plug-in: Martin started, needs some more clean-up (to make it platform independent).
SMS plug-in: Martin started, needs some more clean-up.
UPS plug-in: Martin started, needs some more clean-up.
Weather based rain delay plug-in: Martin started, needs some more clean-up.

In addition, I'd like to have some opinions on the plug-ins. I see we are getting a many plug-ins, which is nice. But, I also see a lot of plug-ins that are completely unrelated to the irrigation system. In addition, many require hardware that is very rare. For example:

SSH client: Has nothing to do with OSPy, Webmin could also provide this.
UPS plug-in: Same holds for this one.
A/D plug-in: Could be used to get temperature readings, but other than that I'm unsure.
Webcam: Might be used to look at the irrigation, but is completely useless for OSPy itself.

I can understand that the current plug-in system is very nice and easy to develop code, but I don't think OSpy is the proper location. Should we keep these plug-ins in the repository under the assumption that others won't enable them anyway, or should we consider (re)moving them? Please let me know what you guys think.

from ospy.

teodoryantcheff avatar teodoryantcheff commented on August 20, 2024

My 2 cents :

  • plugins that are not core should be moved.. e.g. to a separate repo or shipped in the code but not enabled by default
  • same thinking as you about the mobile app integration -- as long as the systems remain incompatible, support for the current mobile app should be dropped. Hopefully some day @salbahra will decide to include support for what ospy has to offer :)

Other than that -- great work, all !

from ospy.

salbahra avatar salbahra commented on August 20, 2024

Just to chime in regarding the mobile app, I would be open to adding support for OSPy fork of OSPi as long as it's being used (by request). Right now, it's too much time to spend on something that's still in an early stage.

I absolutely agree though this looks awesome and love the improvements!

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

Hi, all
SSH client is currently non-functional and can be removed. Yes web cam is used to check irrigation from SMS plugin (send email with photo attachment). I have an Internet connection via a mobile Vodafone LTE. My provider does not allow me a public IP (DynDNS also does not work) because I wanted to have a plugin for SSH connections of raspberry 1 to raspberry 2 (which is the public IP in my home ...)

AD plug used for measuring the temperature in the greenhouse:-)

a) please remove plugins for the move to a temporary folder:
SSH, mobile.

b) I think that plugins do not take up much space and should be delivered in a whole folder OSPy. It is up to the user whether the plugin in settings starts, or let him off.

Yes plugins installation support would also be appropriate (in the future it would be easier for the average user to install a plugin to add to OSPy - installation in the folder plugins and plugins template).

Also, I think it would be appropriate to introduce some help (all plugins) as well as connect hw and how they work.

Thank you all for a great job, I'm excited for the system to "refactor" to start in the spring watering my gardens. MP

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

PS: Je jednodušší spravovat všechny funkce z jednoho místa v rámci integrace (pluginů sms, e-mail, webové kamery plugin plugin, pluginy tlak, Vodní plugin ....
než běží někde v Linuxu na přistýlce webových stránkách ....

Dívám se na OSPy jako malý operační systém:-)
MP

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

sorry:
PS: It is easier to manage all functions from one location within the integration (plugin sms, email plugin, webcam plugin, plugin pressure, watter plugin ....
than running somewhere in Linux on extra website ....

I look at OSPy as a small operating system:-)
MP

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

997f3ca
latest commit
TODO:
Arrange plug-in installation (from zip file?).
for me yes
Add support for plug-ins that want to install packages (properly).
for me yes
Support ospy.service file in setup.py?
for me yes
Thank you for new version...
Martin

from ospy.

Rimco avatar Rimco commented on August 20, 2024

Hi Martin, could you tell me what kind of operating system you are running?
For mine (Raspbian), the ospy.sh works fine. I've read some operating systems use the new style .service file, but I'd need to detect this somehow.

from ospy.

martinpihrt avatar martinpihrt commented on August 20, 2024

Hi,
a) I have raspberry Pi b (512mb) clear installation (Raspbian os) update and upgrade.
b) I clone from: git clone -b refactor https://github.com/Rimco/OSPy
c) open home/pi/OSPy and type: python setup.py install
and first error is web

from ospy.

Rimco avatar Rimco commented on August 20, 2024

That should be fixed now, see #60. My question was regarding:

"Support ospy.service file in setup.py?
for me yes"

Did you use the ospy.service file yet?

from ospy.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.