wake-up-neo.net

Erstellen Sie Google Kalender-Ereignisse aus einer Tabelle, aber vermeiden Sie Duplikate

Ich versuche, ein Skript zu schreiben, das Daten aus einer Google-Tabelle entnimmt und Ereignisse in meinem Google-Kalender erstellt.

Ich habe das gut hinbekommen, aber es hat jedes Mal Duplikate hervorgebracht, wenn ich es ausgeführt habe. Daher versuche ich jetzt, dies zu verhindern, indem ich eine Spalte 17 in der Tabelle mit einer automatisch erstellten eindeutigen Ereignis-ID für jede Zeile erstelle und dann bei jeder Ausführung des Skripts die Ereignis-ID für jede Zeile prüfe und das entsprechende Ereignis lösche im Kalender, bevor Sie es mit den ursprünglichen Daten oder aktualisierten Daten neu erstellen, wenn ich die Zeile geändert habe.

Ich bin neu in der Erstellung von Skripten jeglicher Art und habe dies zusammengeschustert, aber jetzt stoße ich an eine Wand. Kann jemand helfen, dies zu klären?

function CalInsert() {
    var cal = CalendarApp.getDefaultCalendar();
    var id = SpreadsheetApp.getActiveSheet().getRange(2,17).getValue();

    if (id != 0) {
        var event = cal.getEventSeriesById(id);
        event.deleteEventSeries();
    }

    var sheet = SpreadsheetApp.getActiveSheet();
    var startRow = 2; // First row of data to process
    var numRows = sheet.getLastRow(); // Number of rows to process
    var dataRange = sheet.getRange(startRow, 1, numRows, sheet.getLastColumn());
    var data = dataRange.getValues();

    for (i in data) {
        var row = data[i];
        var title = row[0]; // First column
        var desc = row[13]; // Second column
        var tstart = row[14];
        var tstop = row[15];

        var event = cal.createEvent(title, tstart, tstop, {description:desc});
        var eventid = event.getId();
        SpreadsheetApp.getActiveSheet().getRange(2,17).setValue(eventid);
    }
}
26
user2240577

Dies ähnelt einer Frage, die vor zwei Tagen gestellt wurde und sich mit der Synchronisierung einer Tabelle mit Ereignissen mit einem Kalender befasste. Es klingt so, als ob Sie die Tabelle als den Meister der Ereignisse betrachten möchten, von denen sie ausgeht, was das Problem erheblich vereinfachen würde. Die Grundlagen Ihrer Arbeit werden in diese Antwort behandelt. Wenn Sie lieber nur vorhandenen Code ändern möchten, finden Sie unten eine Implementierung.

Ich habe eine geänderte Version des Codes von diesem Blog , mit der bereits vorhandene Kalendereinträge so geändert werden, dass sie mit den Informationen in der Tabelle übereinstimmen. Ich habe meine Tabelle anders angeordnet, was sich im Code widerspiegelt.

Datum | Titel | Startzeit | Endzeit | Standort | Beschreibung | EventID

Die Ereignis-ID-Spalte wird vom Skript beim Erstellen neuer Ereignisse ausgefüllt und dann in späteren Aufrufen zum Abrufen von Ereignissen aus dem Kalender verwendet, um Doppelungen zu vermeiden.

Skript

/**
 * Adds a custom menu to the active spreadsheet, containing a single menu item
 * for invoking the exportEvents() function.
 * The onOpen() function, when defined, is automatically invoked whenever the
 * spreadsheet is opened.
 * For more information on using the Spreadsheet API, see
 * https://developers.google.com/apps-script/service_spreadsheet
 */
function onOpen() {
  var sheet = SpreadsheetApp.getActiveSpreadsheet();
  var entries = [{
    name : "Export Events",
    functionName : "exportEvents"
  }];
  sheet.addMenu("Calendar Actions", entries);
};

/**
 * Export events from spreadsheet to calendar
 */
function exportEvents() {
  var sheet = SpreadsheetApp.getActiveSheet();
  var headerRows = 1;  // Number of rows of header info (to skip)
  var range = sheet.getDataRange();
  var data = range.getValues();
  var calId = "YOUR_CALENDAR_ID";
  var cal = CalendarApp.getCalendarById(calId);
  for (i=0; i<data.length; i++) {
    if (i < headerRows) continue; // Skip header row(s)
    var row = data[i];
    var date = new Date(row[0]);  // First column
    var title = row[1];           // Second column
    var tstart = new Date(row[2]);
    tstart.setDate(date.getDate());
    tstart.setMonth(date.getMonth());
    tstart.setYear(date.getYear());
    var tstop = new Date(row[3]);
    tstop.setDate(date.getDate());
    tstop.setMonth(date.getMonth());
    tstop.setYear(date.getYear());
    var loc = row[4];
    var desc = row[5];
    var id = row[6];              // Sixth column == eventId
    // Check if event already exists, update it if it does
    try {
      var event = cal.getEventSeriesById(id);
    }
    catch (e) {
      // do nothing - we just want to avoid the exception when event doesn't exist
    }
    if (!event) {
      //cal.createEvent(title, new Date("March 3, 2010 08:00:00"), new Date("March 3, 2010 09:00:00"), {description:desc,location:loc});
      var newEvent = cal.createEvent(title, tstart, tstop, {description:desc,location:loc}).getId();
      row[6] = newEvent;  // Update the data array with event ID
    }
    else {
      event.setTitle(title);
      event.setDescription(desc);
      event.setLocation(loc);
      // event.setTime(tstart, tstop); // cannot setTime on eventSeries.
      // ... but we CAN set recurrence!
      var recurrence = CalendarApp.newRecurrence().addDailyRule().times(1);
      event.setRecurrence(recurrence, tstart, tstop);
    }
    debugger;
  }
  // Record all event IDs to spreadsheet
  range.setValues(data);
}

Löschen/Neu erstellen

In dieser Alternative wird die eventID verwendet, um das zuvor vorhandene Ereignis zu suchen und zu löschen. Danach wird ein neues Ereignis mit den Daten in der Tabelle erstellt. Dies hat den Vorteil, dass alle Werte des Ereignisses aktualisiert werden können, einschließlich Start- und Stoppzeiten (siehe Hinweise unten). Andererseits gehen alle am ursprünglichen Ereignis vorgenommenen Änderungen verloren - beispielsweise, wenn andere Personen zu dem Ereignis eingeladen wurden oder benutzerdefinierte Erinnerungen hinzugefügt wurden.

Um diese Alternative zu verwenden, ersetzen Sie einfach den passenden Code durch diesen:

// Check if event already exists, delete it if it does
try {
  var event = cal.getEventSeriesById(id);
  event.deleteEventSeries();
  row[6] = '';  // Remove event ID    
}
catch (e) {
  // do nothing - we just want to avoid the exception when event doesn't exist
}
//cal.createEvent(title, new Date("March 3, 2010 08:00:00"), new Date("March 3, 2010 09:00:00"), {description:desc,location:loc});
var newEvent = cal.createEvent(title, tstart, tstop, {description:desc,location:loc}).getId();
row[6] = newEvent;  // Update the data array with event ID
debugger;

Anmerkungen

  • Die Dokumentation für getEventSeriesById gibt fälschlicherweise null zurück, wenn kein passendes Ereignis gefunden wird, und löst stattdessen eine Ausnahme aus. (böse!) Also habe ich es in einen Versuchs-/Fangblock eingeschlossen, nur um weiter zu schwimmen.
  • Leider ist getEventSeriesById beim Abrufen eines Ereignisses returns ein EventSeries -Objekt, das die setTime() -Methode nicht unterstützt. Wenn Sie nicht damit rechnen, die Uhrzeit der Ereignisse zu ändern, klicken Sie auf OK. Andernfalls können Sie das Event in ein EventSeries ändern, indem Sie die Wiederholung Regeln und Zeiten festlegen, oder das alte Ereignis löschen und ein neues erstellen, wie gezeigt in Löschen/Neu erstellen . Ausgabe 1154 .
  • Die Tabelle gewinnt immer. Event-Änderungen (in relevanten Feldern), die über den Google Kalender aufgezeichnet wurden, werden vom Skript überschrieben.
38
Mogsdad

Ich möchte dies für jeden veröffentlichen, der es verwenden möchte. Ich habe das Skript so geändert, dass es in einem Blatt funktioniert, das ich bereits verwendet habe. Das Datumsformat und das Duplizieren von Ereignissen waren einige Probleme, die behoben werden mussten, aber nach einigen Tests bin ich ziemlich zufrieden mit der Funktionsweise. Ich buche damit Jobs und teile sie mit meinen Mitarbeitern, die mobil sind und Bauarbeiten in der gesamten Region ausführen Stadt. Der nächste Schritt besteht darin, Kalenderereignisse in die Tabelle zu ziehen, damit sie in beide Richtungen funktionieren. Ich kann die Kalender-App auf meinem Telefon verwenden, um Jobs im Handumdrehen zu buchen. Wenn also jemand Ratschläge hat, brauche ich auch noch ein Skript zum Einfügen Formulieren Sie Antwortdaten in dasselbe Blatt und fügen Sie vollständige Zeilen hinzu, in denen die Auftragsnummern übereinstimmen, wobei die vorhandenen Daten erhalten bleiben.

`function onOpen() {
var sheet = SpreadsheetApp.getActiveSpreadsheet();
var entries = [{
name : "Export Events",
functionName : "exportEvents"
}];     sheet.addMenu("Calendar Actions", entries);
};

function parseDate(s) {
var months = {jan:0,feb:1,mar:2,apr:3,may:4,jun:5,
            jul:6,aug:7,sep:8,oct:9,nov:10,dec:11};
var p = s.replace(".", "").split('-');
return new Date(p[2], months[p[1].toLowerCase()], p[0]);
}

/**
* Export events from spreadsheet to calendar
*/
function exportEvents() {
var sheet = SpreadsheetApp.getActiveSheet();

var headerRows = 6;  // Number of rows of header info (to skip)
var range = sheet.getDataRange();
var data = range.getDisplayValues();
//var calId = "Your calendar Id"; // PRODUCTION
var calId = "Your_calendar Id to test"; // TEST
var cal = CalendarApp.getCalendarById(calId);
//Logger.log(cal);
//Logger.log(data.length);
for (i=0; i<data.length; i++) {
if (i < headerRows) continue; // Skip header row(s)
if (data[i][0].length < 1) continue; // Skip if no content.

var row    = data[i];
Logger.log(row);
var date   = parseDate(row[0]);  // First column
//Logger.log(date);
var title  = row[1];           // Second column

var tstart = new Date();
var s = row[2].split(":");
tstart.setHours(s[0]);
tstart.setMinutes(s[1]);
tstart.setSeconds(s[2]);
tstart.setDate(date.getDate());
tstart.setMonth(date.getMonth());
tstart.setYear(date.getYear());

var tstop = new Date();
var e = row[3].split(":");
tstop.setHours(e[0]);
tstop.setMinutes(e[1]);
tstop.setSeconds(e[2]);

tstop.setDate(date.getDate());
tstop.setMonth(date.getMonth());
tstop.setYear(date.getYear());
var loc  = row[4];
var desc = row[5];
var id   = row[6];              // Sixth column == eventId
// Check if event already exists, update it if it does
var event = null;
if (id.length > 0) {
try {
event = cal.getEventSeriesById(id);
}
catch (e) {
// do nothing - we just want to avoid the exception when event doesn't            exist
} 
}
if (!event) {
//cal.createEvent(title, new Date("March 3, 2010 08:00:00"), new
Date("March 3, 2010 09:00:00"), {description:desc,location:loc});
var newEvent = cal.createEvent(title, tstart, tstop,                                     
{description:desc,location:loc}).getId();                     
var r = i + 1;
var cell = sheet.getRange("G" + r);
cell.setValue(newEvent);
}
else {
Logger.log(event);
event.setTitle(title);
event.setDescription(desc);
event.setLocation(loc);
// event.setTime(tstart, tstop); // cannot setTime on eventSeries.
// ... but we CAN set recurrence!
var recurrence = CalendarApp.newRecurrence().addDailyRule().times(1);
event.setRecurrence(recurrence, tstart, tstop);
}
debugger;
}
}

`

4
Jarrod Rapson