如何在iOS应用中实现Google Calendar的事件读写功能?
嘿,刚上手Xcode 9的话,对接Google Calendar实现读写其实没你想的那么难,我给你梳理下核心的实现步骤,一步步来就好:
第一步:搞定Google Cloud平台的基础配置
这是对接API的前提,必须先做:
- 去Google Cloud Console创建一个新项目,找到并启用Google Calendar API——只有启用了这个API,你的应用才能调用读写接口。
- 创建OAuth 2.0客户端ID,选择iOS类型,填写你Xcode项目里的Bundle ID(就是项目设置里那个唯一标识,填错了会导致授权失败)。
- 下载生成的
GoogleService-Info.plist文件,拖进Xcode项目,勾选对应的target,确保项目能读取到这个配置文件。
第二步:用CocoaPods集成Google相关SDK
Xcode 9一般用CocoaPods管理依赖,所以在你的Podfile里加上这两个库:
pod 'GoogleSignIn' # 处理用户登录授权 pod 'GoogleAPIClientForREST/Calendar' # Google Calendar的REST API客户端
然后在终端跑pod install,之后一定要用生成的.xcworkspace文件打开项目,别再用.xcodeproj了。
第三步:实现用户授权登录
访问Google Calendar必须经过用户授权,所以先搞定登录:
- 在
AppDelegate里初始化GoogleSignIn:
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool { // 从GoogleService-Info.plist里取clientID,也可以手动填 GIDSignIn.sharedInstance().clientID = "<你的OAuth客户端ID>" GIDSignIn.sharedInstance().delegate = self return true }
- 处理登录回调的URL,在
AppDelegate里加这个方法:
func application(_ app: UIApplication, open url: URL, options: [UIApplication.OpenURLOptionsKey : Any] = [:]) -> Bool { return GIDSignIn.sharedInstance().handle(url) }
- 在你的登录页面加个Google登录按钮,或者自己写个触发登录的逻辑:
// 比如给一个UIButton加点击事件 @IBAction func googleLoginTapped(_ sender: UIButton) { GIDSignIn.sharedInstance().signIn() }
- 实现
GIDSignInDelegate协议,处理登录成功/失败的情况:
extension AppDelegate: GIDSignInDelegate { func sign(_ signIn: GIDSignIn!, didSignInFor user: GIDGoogleUser!, withError error: Error!) { if let error = error { print("登录失败:\(error.localizedDescription)") return } // 登录成功,这里可以跳转到你的主页面,开始处理Calendar操作 print("用户登录成功:\(user.profile.name ?? "")") } }
第四步:读取Google Calendar的事件
登录成功后,就可以调用API拉取事件了:
- 先初始化Calendar服务对象,绑定用户的授权信息:
let calendarService = GTLRCalendarService() calendarService.authorizer = GIDSignIn.sharedInstance().currentUser?.authentication.fetcherAuthorizer()
- 构建查询请求,比如获取未来7天的主日历事件:
let query = GTLRCalendarQuery_EventsList.query(withCalendarId: "primary") // primary代表用户的主日历,如果要访问其他日历,需要替换成对应的日历ID query.timeMin = GTLRDateTime(date: Date()) query.timeMax = GTLRDateTime(date: Date().addingTimeInterval(7*24*60*60)) // 7天后的时间 query.maxResults = 10 // 最多返回10条事件 query.singleEvents = true // 把重复事件拆分成单个实例 query.orderBy = kGTLRCalendarOrderByStartTime // 按开始时间排序
- 执行查询并处理结果:
calendarService.executeQuery(query) { (ticket, response, error) in if let error = error { print("获取事件失败:\(error.localizedDescription)") return } guard let eventsResponse = response as? GTLRCalendar_Events, let events = eventsResponse.items else { print("没有找到事件") return } // 遍历事件,处理数据 for event in events { let title = event.summary ?? "无标题" let startTime = event.start?.dateTime?.date ?? Date() print("事件:\(title),开始时间:\(startTime)") // 这里可以把事件数据转成你的模型,展示到UI上 } }
第五步:向Google Calendar写入事件
同样用上面的calendarService对象,创建事件并提交:
- 先构建
GTLRCalendar_Event对象,设置事件的基本信息:
let newEvent = GTLRCalendar_Event() newEvent.summary = "我的测试事件" // 事件标题 newEvent.descriptionProperty = "这是通过iOS应用创建的Google Calendar事件" // 事件描述 // 设置开始时间 let startDateTime = GTLRCalendar_EventDateTime() startDateTime.dateTime = GTLRDateTime(date: Date().addingTimeInterval(2*60*60)) // 2小时后开始 startDateTime.timeZone = TimeZone.current.identifier // 用当前时区 // 设置结束时间 let endDateTime = GTLRCalendar_EventDateTime() endDateTime.dateTime = GTLRDateTime(date: Date().addingTimeInterval(3*60*60)) // 持续1小时 endDateTime.timeZone = TimeZone.current.identifier newEvent.start = startDateTime newEvent.end = endDateTime
- 构建插入请求并执行:
let insertQuery = GTLRCalendarQuery_EventsInsert.query(withObject: newEvent, calendarId: "primary") calendarService.executeQuery(insertQuery) { (ticket, response, error) in if let error = error { print("创建事件失败:\(error.localizedDescription)") return } guard let createdEvent = response as? GTLRCalendar_Event else { print("事件创建失败") return } print("事件创建成功!事件ID:\(createdEvent.identifier ?? "")") // 这里可以给用户弹出提示,告诉他们事件创建成功 }
一些新手容易踩的坑
- 别忘了在
Info.plist里添加LSApplicationQueriesSchemes,包含comgoogleauth,不然登录跳转回应用会失败。 - Xcode 9对应的Swift版本是4.0,代码里要注意语法兼容性,比如可选值的解包、闭包的写法。
- 测试的时候要确保设备能访问Google服务,国内环境可能需要特殊网络,你懂的。
- 记得处理用户登出的逻辑,比如调用
GIDSignIn.sharedInstance().signOut()清空授权信息。
内容的提问来源于stack exchange,提问作者Don Oleksa
相关产品推荐
相关产品推荐

