首页 > 其他分享 >#2 Context and Event

#2 Context and Event

时间:2024-03-24 22:36:36浏览次数:14  
标签:context Context 取消 page func cancel Event 页面

这个例子演示了初始化一个新的浏览器实例,打开 GitHub 首页,并演示如何在等待页面事件时处理上下文取消的情况。

package main

import (
	"context"
	"fmt"
	"time"

	"github.com/go-rod/rod"
	"github.com/go-rod/rod/lib/proto"
)

func main() {
	browser := rod.New().MustConnect()
	defer browser.MustClose()

	page := browser.MustPage("https://github.com").MustWaitLoad()

	page, cancel := page.WithCancel()

	go func() {
		time.Sleep(time.Second)
		cancel()
	}()

	// It's a blocking method, it will wait until the context is cancelled
	page.EachEvent(func(_ *proto.PageLifecycleEvent) {})()

	if page.GetContext().Err() == context.Canceled {
		fmt.Println("cancelled")
	}
}

前面关于浏览器和页面的相关操作就不再赘述,着重说一下取消上下文的部分。

page, cancel := page.WithCancel()
  • func (b *Browser) WithCancel() (*Browser, func())。这是WithCancel()方法的原型,返回两个返回值,其中page属于Browser类型的指针,cancel属于一个函数。
  • 这行代码做的事情
    • 创建新的上下文:它复制当前页面对象并关联一个新的可取消的上下文(context.WithCancel)。这意味着返回的 page 变量现在具有一个与之关联的取消函数。
    • 获取取消函数:变量 cancel 是一个函数,当你调用它时,与新 page 对象关联的所有操作都将被取消。这对于中断不再需要完成的页面加载或其他长时间运行的任务非常有用。
  • 这个功能特别适合于以下几种情况:
    • 限时操作:如果你有一个页面操作,比如数据抓取或等待元素出现,但你希望在超过特定时间后自动取消这个操作,可以使用 WithCancel 来实现。
    • 条件取消:在某些情况下,你可能基于外部事件或条件判断需要中断页面操作。例如,用户取消操作或者程序在其他地方遇到错误需要停止当前操作。
go func() {
		time.Sleep(time.Second)
		cancel()
	}()
  • 启动一个新的goroutine,其中是一个匿名函数。
  • 先调用time.Sleep(time.Second),等待1秒钟,也就是暂停当前goroutine的执行1秒钟。
  • 然后调用cancel(),这个cancel函数就是上面的page.WithCancel()获得的,用于取消所有与page相关的挂起操作。
page.EachEvent(func(_ *proto.PageLifecycleEvent) {})()
  • page.EachEvent(...):这是 go-rod/rod 库中的一个方法,用于订阅一个或多个特定类型的浏览器事件。在这个上下文中,它用于监听页面的生命周期事件。
  • func(_ \*proto.PageLifecycleEvent) {}:这是传递给 EachEvent 方法的回调函数,用于处理页面生命周期事件。回调函数的参数是指向 proto.PageLifecycleEvent 类型的指针,这代表了一个页面生命周期事件。在函数参数列表中的下划线 _ 表示这个参数在函数体内不会被使用。函数体 {} 是空的,意味着当事件发生时,没有任何操作会被执行。
  • 调用 page.EachEvent(func(_ *proto.PageLifecycleEvent) {})() 会导致代码执行在这里阻塞,等待事件发生。但是,由于回调函数不处理任何事件(因为它的函数体为空),这个调用实际上会一直等待,直到页面的上下文被取消。
if page.GetContext().Err() == context.Canceled {
		fmt.Println("cancelled")
	}
  • 这是在Go(Golang)中处理操作被取消的一种常见模式,通常用于需要提前中止的Web服务器或任何并发操作中。
  • page.GetContext(): 这个函数假定是用来获取与page对象相关联的context.Context。在Go中,Context用于在API边界和进程之间传递截止日期、取消信号和其他请求范围的值。
  • .Err(): 这个方法在context.Context对象上,如果上下文已被取消或超时,则返回一个错误。
  • context.Canceled: 这是一个预定义的错误,表示上下文被取消了。

标签:context,Context,取消,page,func,cancel,Event,页面
From: https://www.cnblogs.com/Edward6/p/18093223

相关文章

  • HTML DOM的event事件
    onabort图像的加载被中断 onblur 元素失去焦点onchange域的内容被改变onclick当用户点击某个对象时调用的事件句柄ondblclick 当用户双击某个对象时调用的事件句柄onerror在加载文档或图像时发生错误 onfocus元素获得焦点onkeydown某个键盘按......
  • WinAppSDK / WinUI3 项目无法使用 SystemEvents 的问题
    SystemEvents是一个开发win32窗口项目很常用的类,其中封装了一些常用的系统广播消息。在WinUI3项目中,SystemEvents事件经常无法触发,简单排查了一下原因。SystemEvent内封装了一个线程和一个窗口,通过窗口消息在内部线程上调用事件,内部使用了SystemEventInvokeInfo对象来保......
  • docker context 介绍
    $dockercontextlsNAMEDESCRIPTIONDOCKERENDPOINTERRORdefaultCurrentDOCKER_HOSTbasedconfigurationunix:///var/run/docker.sockdesktop-linuxDockerDesktop......
  • CanvasRenderingContext2D: setLineDash() method格式说明
    定义setLineDash(segments)segments一个数组,用于指定交替绘制直线和间隙的距离(以坐标空间单位表示)。如果数组中元素的个数是奇数,数组中的元素会被复制并连接起来。例如,[5,15,25]将变成[5,15,25,5,15,25]。如果数组为空,破折号列表将被清除,行描边将恢复为实线。例子......
  • EventSourceResponse
    EventSourceResponse 是来源于 sse-starlette 库的一个类,它主要用于构建Server-SentEvents(SSE)响应。Server-SentEvents是一种允许服务器向浏览器发送实时更新的技术,常用于实现实时推送通知、股票报价更新、聊天应用等场景。在Starlette和FastAPI等基于异步的Web框架......
  • 微信公众号开发 - 扫描带参数二维码事件支持EventKey字符串传参
    $access_token=$this->access_token();//获取access_token$json_url='https://api.weixin.qq.com/cgi-bin/qrcode/create?access_token='.$access_token;$scene_id="A123B";$curl_data='{"action_name&......
  • MindSpore报错处理:TypeError: For 'set_context', the parameter device_id can not b
    问题背景在使用MindSpore运行一个分子动力学模拟的测试程序时:frommindsporeimportcontextfrommindspore.nnimportAdamif__name__=="__main__":importsyssys.path.insert(0,'../..')fromspongeimportSponge,Molecule,ForceField,set_global......
  • react router v6报错 useRoutes() may be used only in the context of a <Router> comp
    在使用reactrouterv6版本的时候,按照之前的方法使用src/main.tsx是这样的,几乎不动import*asReactfrom"react";import*asReactDOMfrom"react-dom/client";import"~/assets/index.css";importAppfrom"~/App.tsx";ReactDOM.createRoot(......
  • spring refresh的流程(AbstractApplicationContext的refresh方法)
    12个阶段1、prepareRefresh,做准备工作2、obtainFreshBeanFactory,创建或获取beanfactory3、prepareBeanFactory,准备beanfactory4、postProcessBeanFactory,子类扩展beanfactory5、invokeBeanFactoryPostProcessors,后处理器扩展beanfactory6、registerBeanPostProcessors,准备b......
  • WPF MVVM模式ListBox下ContextMenu绑定Command的方法以及将所选的Item的数据传回去
    需求:ListBoxItem上右键,将数据传参。疑问:ContextMenu不继承DataContext,导致直接用RelativeSource找根的方式也绑定不到。解决方法:在ListBox.ContextMenu里写菜单,就可以直接绑定到ViewModel层的命令了,参数先用RelativeSource找到ContextMenu,再绑定PlacementTarget.SelectedItem。......