External Bind

From Davical
Revision as of 10:38, 6 July 2020 by Stephan (talk | contribs)
Jump to navigationJump to search

starting with version 0.9.9.5 it is now possible to import a remote calendar that is available from the web. To enable this feature you must add the external_refresh configuration parameter:

Configuration in config.php

/*
* External subscription (BIND) minimum refresh interval
* Required if you want to enable remote binding ( webcal subscriptions )
* Default: none
*/
$c->external_refresh = 60; // Minutes

That is the minimum time period to wait between checks to see if the remote file has been updated, it will only be refreshed when

  1. client tries to look at the calendar,
  2. the last update was more than $c->external_refresh minutes ago,
  3. the remote server indicates the file has been updated it will reimport the calendar.

Note that you need the php5-curl package (Debian/Ubuntu, other distros might call it differently) for this to work otherwise you get 500 errors when querying the calendar. With that setting in place it is possible to bind a remote calendar:

External Bind in the Admin Interfacde

  1. Make sure you're using Davical 1.1.5 or higher
  2. Go to Principal Details (e.g. User Functions --> View my Details)
  3. You'll find a section called "Bindings to other collection"
  4. Existing bindings are listed here. The input fields in the bottom line will allow you to add new bindings:
    • ID: An internal ID
    • Bound as: The relative path assigned to a bound collection
    • DisplayName: The name you want to assign to the bound collection
    • To Collection: This is the actual address of the collection you want to bind:
      • Existing bindings: An internal relative path in the form of /.external/[xyz] is shown here.
      • Setting up: Enter a valid and working collection URL like https://myExternalCalendar/public.ics into this field.
  5. You want to set up a new binding? Fill in the fields, press the "create" button and the binding will be created. The external URL field gets converted to a relative path in the process.
    • Your external URL doesn't get converted? Check (and double check...) that the external URL is valid and available to your Davical server.


Manually setting up an External Bind

Prior to version 1.1.5, External Binds can only be set up through a CalDAV BIND request. That request should look similar to the following:

BIND https://example.org/caldav.php/user/

<?xml version="1.0" encoding="utf-8"?>
<dav:bind xmlns:dav="DAV:">
<dav:segment>Melbourne Rebels 2011 Fixtures</dav:segment><dav:href>http://www.me.com/ca/sharesubscribe/1.282129618/731F31CB-B333-43A7-9A79-78F785CDF767.ics</dav:href></dav:bind>

That request will create a calendar named "Melbourne Rebels 2011 Fixtures" in https://example.org/caldav.php/user/ with the contents imported from http://www.me.com/ca/sharesubscribe/1.282129618/731F31CB-B333-43A7-9A79-78F785CDF767.ics.

One can generate such a request with curl using the following:

USERNAME=yourusername:yourpassword
CALENDAR=http://mycal.example.net/calendar/caldav.php/yourusername/
REMOTE=http://www.example.org/calendar/file.ics
CALNAME="Remote Calendar"
curl --basic --user "${USERNAME}" -X BIND -H "Content-Type: text/xml" --url "${CALENDAR}" -d "<?xml version='1.0' encoding='utf-8'?><bind xmlns='DAV:'><segment>${CALNAME}</segment><href>${REMOTE}</href></bind>"

Performance considerations

This can generate a fair amount of load on the server, so I wouldn't suggest using a lot of these with a short refresh interval. They are shared between users based on the md5 of the remote url, so five users subscribing to the same calendar will all see the same data. Finally there is currently no provision for removing them or the data when no one actually bound to them, since no one is requesting updates they will just be taking space in the database the following should list them so they can be cleaned up.

select dav_name from collection where parent_container='/.external/' and collection_id not in ( select bound_source_id from dav_binding where external_url is not null);