I am practicing Python and wanna create an own skill.
This skill should access to a Nextcloud Calender. I should do prompts and new entries etc.
I create a new skill with the template mycroft-msk create and initially it works. I can make promts etc. but whenever I modify my __init__.py and try to extend it, the prompts are not working anymore.
For now I have just this snippet here
``` `` `
from mycroft import MycroftSkill, intent_file_handler
import caldav
from caldav.elements import dav
caldav_url = 'url'
class SiCalender(MycroftSkill):
def __init__(self):
MycroftSkill.__init__(self)
def initialize(self):
self._username = str(self.settings.get("username"))
self._password = str(self.settings.get("password"))
# open connection to calendar
client = caldav.DAVClient(url=caldav_url, username=self._username, password=self._password)
principal = client.principal()
# get all available calendars (for this user)
calendars = principal.calendars()
for c in calendars:
self.log.info('got calendar {}'.format(c.name))
@intent_file_handler('calender.si.intent')
def handle_calender_si(self, message):
self.speak_dialog('calender.si')
def create_skill():
return SiCalender()
```````` `` `
Whenever I add the initialize the skill does not work anymore…
What am I doing wrong?
i think you have to add additional steps between the Principal object creation and calling calendars() on em, because it would return self.calendar_home_set.calendars() and self.calendar_home_set is None after initialisation - and is from what i can gather not set subsequently. This should causing the problem.
I think whenever I try to modify the __init__.py the skill is not working anymore and I have to delete it and create a new one…
Now I try to get the username and password which can be set in the settings.
class SiCalender(MycroftSkill):
def __init__(self):
MycroftSkill.__init__(self)
def initialize(self):
self.register_entity_file('when.entity')
self.setting_change_callback = self.on_websettings_changed
self.on_websettings_changed()
def on_websettings_changed(self):
self.log.info('Collecting login information')
self.user = self.settings.get('username')
if not self.user:
self.log.info('Failed to retrieve username')
self.password = self.settings.get('password')
if not self.password:
self.log.info('failed to retrieve password')
self.log.info('Completed login information retrieval attempt')
@intent_file_handler('calender.si.intent')
def handle_calender_si(self, message):
self.speak_dialog('calender.si')
def create_skill():
return SiCalender()
But this snippet seems also not working.
I don’t get it
With not working I mean, I cannot even do a prompt like “What is my next appointment” MyCroft is supposed to answer “No appointments today” for now but always reply “I don’t understand” etc.
class SiCalender(MycroftSkill):
def __init__(self):
MycroftSkill.__init__(self)
self.log.info('Collecting login information')
self.user = self.settings.get('username')
if not self.user:
self.log.info('Failed to retrieve username')
self.password = self.settings.get('password')
if not self.password:
self.log.info('failed to retrieve password')
@intent_file_handler('calender.si.intent')
def handle_calender_si(self, message):
self.speak_dialog('calender.si')
def create_skill():
return SiCalender()
Also did not work. Always answer that he cannot understand me.
But when I create a skill from template it worked…
I uninstalled that skill and reinstalled again and it is my skill folder on the pi but not on the skill settings on mycroft home for some reason…
But when I create a new skill from template the skill appears in the home but uninstalling and installing again with mycroft-msm install skill it doesn’t appear…
The skeleton skill is working, if you toss everything caldav related.
i’m struggling with ssl. requests is excepting because my ssl cert is expired (allthough it’s not) - most likely the expiration of the CAcertificate (LetsEncrypt resp. IdenTrust). certifi is the package handling that in given context. (Docker/npm issue)
Furthermore config.php (nextcloud) would need an trusted_domain addition (if the IP calling from is not allready listed)
edit: i’m unclear if the url you want to call is wrong. It might be that you have to call ../remote.php/dav/calendars/< user >/
yeah, just want to update that the skill is working with the code on github as is.
With the slight difference that i don’t use the webend to store and retrieve the settings - but that is not the issue (you don’t need to str() the settings btw). And i tossed the caldav.elements import.
Due to the fact that i use (homebrew) SSL i pass the param ssl_verify_cert="/path/to/ca.pem"
so calendars would be [Calendar(https://.../remote.php/dav/calendars/<redacted>/personal/)] in my case (only have the default calendar)
This could mean, that one of the above mentioned problems occur.
SSL (verify resp. verify_ssl_cert is True by default),
Nextcloud not trusting the IP/host → trusted_domains
You might want to check /var/log/mycroft/skills.log. I would expect exceptions during startup.
DAVClient is handling this, so you can stay with the former expression (without knowing if DAVClient is able to obectify the url as quoted above)
On a general note, i wouldn’t use the web backend settings for sensitive information. (saw the credentials.py btw) You might want to look into using OAuth described here. This skill is worth a peek for oauth implementation. (concerning access token/user agent mycroft wise)
But i’m unclear about the “redirect uri” from nextcloud tbh.
depending on your webserver setup there should be a config file at /var/www/html/nextcloud/config/config.php. A host/ip declaration in trusted_domains is needed to be able to connect.
And not be able to connect would equate to an exception, ie skill wont load (you might want to use try: except: here; and self.speak_dialog("not_connected") if that happens - just to get some audio feedback)
if you want the error to be spoken
except Exception as e:
error = str(e)
self.speak_dialog('not_connected',
data={"error": error})
with not_connected.dialog (in locale)
“Nicht verbunden. Grund {error}”
You might want to check /var/log/mycroft/skills.log. I would expect exceptions during startup.
How can I check the skills.log?
I am not so familar with Linux and opened the file with vim but I think this is not a good way to check log files…
depending on your webserver setup there should be a config file at /var/www/html/nextcloud/config/config.php. A host/ip declaration in trusted_domains is needed to be able to connect.
I see! The webserver is hosted from my univ, so I can’t change anything there
So when an import is not correctly loaded or when there is an exception the whole skill is not working, right?
Do you know the admin? Better person to ask than some guy who is bruteforcing his way through everything network related
hdm-stuttgart. realized that. That is why i mentioned Oauth. I would guess an authorisation method like this is more appreciated(?) by the admins than ping-ponging the credentials back and forth. Again, the admin would be the right guy to ask.
You can go all in with one of those but i didn’t felt the need (until now - damn you). Talking Mycroft-native stuff, there are a few commands using mycroft-cli-client like :find 'Exception' but this is mostly real-time (i wouldn’t know how long you can stretch the period pre startup with :history #lines ; maybe @gez-mycroft can jump in)
If you are looking at the gcalendar skill, Ake has set an event in init. If this event (that calls the relevant method) throws an exception, the skill (in general) wouldn’t care much - besides not doing what it’s told. But i wouldn’t miss try/except those exceptions because it gives an opportunity to get some audio feedback.
I cobble together an implementation for my reminder skill as we speak and send you the git link if you like.
With the reminder skill i’m going a similar route with handling the dav calendars (pulling the events and saveing the new ones locally) when the skill regularly checks the reminders.
Yeah I could ask the admin.
But I thought it is a valid method to save the credentials in the backend (home mycroft) and fetch it with settings.get .
If this event (that calls the relevant method) throws an exception, the skill (in general) wouldn’t care much - besides not doing what it’s told
Hmm I see. But then I still don’t understand why my skill wasn’t working when I did the import caldav…
> I cobble together an implementation for my reminder skill as we speak and send you the git link if you like.
Ah yes please, that would be nice!
I want to implement basic actions like asking mycroft “what are my appointments for today, what is my next appointment”,
Creating new appointments for day X, deleting appoinments.
I think it is not difficult but I am having trouble already with the connection of the calendar…
its not the local storage that is problematic, more requesting the server with username:password. (and not being a intranet/local network call)
That wasn’t the cause, but using the import in initialize (by creating an calendar object - that was somehow bugging out) - but we still not know if/where/why the exception happend
Creating ical data from a mycroft reminder or some other input for that matter isn’t that straight forward - at least not with caldav 0.8.2(latest). You need to work with Event /Calendar class from icalendar. Otherwise you would have to string it together (which is impractical).
Got it to push the new reminder to the server. I even see the PUT request with a 201 response (Created) but nothing appears on the personal calendar. The other way around is no problem. I’ll look tomorrow what’s up with that. Maybe some crucial subcomponent is missing
edit: got it. Nextcloud has no clue what to do with VALARM (the prenotify component). I guess the timedelta data threw em off. Yet, i could retrieve the event that wasn’t shown
That wasn’t the cause, but using the import in initialize (by creating an calendar object - that was somehow bugging out) - but we still not know if/where/why the exception happend
I see.
Could you help me with what you did so that the skill is running?
I guess you have to help me first and look in skills.log what is going on. (And i would think the solution is not skill related but Nextcloud config related, or if it is SSL then it’s Linux related)