C# 为什么删除google日历条目/事件时entry.delete()为400?

C# 为什么删除google日历条目/事件时entry.delete()为400?,c#,mono,google-calendar-api,C#,Mono,Google Calendar Api,验证、搜索和向google日历添加事件/实体的工作正常,但删除会导致400个错误请求 代码大部分是从中复制的 googleUri下面是指向该应用程序/用户创建的日历项的链接,标题为“要删除的事件”,应删除该事件,ConfigurationManager.AppSettings包含身份验证信息 调试输出显示已找到日历项,但删除未成功 这将使用谷歌日历API v2,该API在发布之前应仍能正常运行。迁移到v3会很好,但据我所知,它没有提供使用已知用户+密码进行身份验证的方法,而是使用需要手动输入go

验证、搜索和向google日历添加事件/实体的工作正常,但删除会导致400个错误请求

代码大部分是从中复制的

googleUri下面是指向该应用程序/用户创建的日历项的链接,标题为“要删除的事件”,应删除该事件,ConfigurationManager.AppSettings包含身份验证信息

调试输出显示已找到日历项,但删除未成功

这将使用谷歌日历API v2,该API在发布之前应仍能正常运行。迁移到v3会很好,但据我所知,它没有提供使用已知用户+密码进行身份验证的方法,而是使用需要手动输入google凭据的过期令牌

Debug.Write ("want to remove: " + googleURI);

// autheticate and get service
CalendarService svc = new CalendarService(ConfigurationManager.AppSettings["GoogleCalendarName"]);
svc.setUserCredentials(ConfigurationManager.AppSettings["GoogleCalendarUsername"], ConfigurationManager.AppSettings["GoogleCalendarPassword"]);
svc.QueryClientLoginToken();

// find the event(s) -- should only be one that can match the googleuri
EventQuery evtquery = new EventQuery(ConfigurationManager.AppSettings["GoogleCalendarPostURI"]);
evtquery.Uri = new Uri(googleURI);
EventFeed evtfeed = svc.Query (evtquery);

//should only be one event in the query
if (evtfeed == null || evtfeed.Entries.Count != 1) {
Debug.Write ("No match or too many matches for " + googleURI); // if this is less than 1, we should panic
    return;
}

// we found the right one
EventEntry entry = (EventEntry)(evtfeed.Entries[0]);
Debug.Write ("Title: " + entry.Title.Text);

//hangs here until "The remote server returned an error: (400) Bad Request.
entry.Delete(); 
输出为:

[0:] want to remove: https://www.google.com/calendar/feeds/default/private/full/77e0tr0e3b4ctlirug30igeop0
[0:] Title: Event To Delete
我也尝试过使用批处理方法来避免avial

// https://developers.google.com/google-apps/calendar/v2/developers_guide_dotnet?csw=1#batch
// Create an batch entry to delete an the appointment
EventEntry toDelete = (EventEntry)calfeed.Entries[0];
toDelete.Id = new AtomId(toDelete.EditUri.ToString());
toDelete.BatchData = new GDataBatchEntryData("Deleting Appointment", GDataBatchOperationType.delete);


// add the entry to batch

AtomFeed batchFeed = new AtomFeed(calfeed);

batchFeed.Entries.Add(toDelete);


// run the batch

EventFeed batchResultFeed = (EventFeed)svc.Batch(batchFeed, new Uri(ConfigurationManager.AppSettings["GoogleCalendarPostURI"]  ));


// check for succses

Debug.Write (batchResultFeed.Entries [0].BatchData.Status.Code);

if (batchResultFeed.Entries [0].BatchData.Status.Code != 200) {
   return;
}

我无法弄清楚v2到底发生了什么,但我能够使用服务帐户进行身份验证,将api迁移到v3

using System;

using Google.Apis.Calendar.v3;
using Google.Apis.Calendar.v3.Data;
// for BaseClientService.Initializer
using Google.Apis.Services;
// provides ServiceAccountCredential
using Google.Apis.Auth.OAuth2; 
// read in cert
using System.Security.Cryptography.X509Certificates;


namespace LunaIntraDBCalTest
{
    public class Program
    {
        public static string calendarname = "xxxx@gmail.com"; //address is default calendar
        public static string serviceAccountEmail = "yyyy@developer.gserviceaccount.com";

        public static CalendarService getCalendarService(){



            // certificate downloaded after creating service account access at could.google.com
            var certificate = new X509Certificate2(@"key.p12", "notasecret", X509KeyStorageFlags.Exportable);

            // autheticate
            ServiceAccountCredential credential = new ServiceAccountCredential(
                new ServiceAccountCredential.Initializer(serviceAccountEmail)
                {
                    Scopes = new[] { CalendarService.Scope.Calendar }
                }.FromCertificate(certificate));

            // Create the service.
            var service = new CalendarService(new BaseClientService.Initializer()
                {
                    HttpClientInitializer = credential,
                    ApplicationName = "LunaIntraDB",
                });

            return service;
        }

        // create event object that will later be inserted
        public static Event createEvent(string Summary, string Location, string Description, DateTime ApptDateTime, double duration ){
            // create an event
            Event entry= new Event
            {
                Summary = Summary,
                Location = Location,
                Description = Description,
                Start = new EventDateTime { DateTime = ApptDateTime },
                End = new EventDateTime { DateTime = ApptDateTime.AddHours(duration) },
            };

            return entry;
        }

        // capture event ID after inserting
        public static string insertEvent(Event entry){
            var service = getCalendarService ();
            EventsResource.InsertRequest insert = service.Events.Insert (entry, calendarname);
            // TODO: try catch here; will be throw exception if bad datetime
            return insert.Execute().Id;
        }

        public static void deleteEvent(string id){
            // TODO CATCH IF NOT FOUND
            // to have access to this calendar, serviceAccountEmail needed permission set by ownner in google calendar
            //Calendar cal1 = service.Calendars.Get (calnedarname).Execute();
            var service = getCalendarService ();
            service.Events.Delete (calendarname, id).Execute ();
        }

        public static void Main(string[] args)
        {

            // create event
            var entry = createEvent ("TEST", "here", "this is a test", DateTime.Now, 1.5);

            string id = insertEvent (entry);
            Console.WriteLine("Run to your calendar to see that this event was created... (any key after checking)");
            Console.ReadKey();

            deleteEvent (id);
            Console.WriteLine("Should now be deleted!... (any key to close)");
            Console.ReadKey();
        }
    }
}