Best Syzkaller code snippet using main.TestBisectCause
bisect_test.go
Source:bisect_test.go
...9 "time"10 "github.com/google/syzkaller/dashboard/dashapi"11 "github.com/google/syzkaller/pkg/email"12)13func TestBisectCause(t *testing.T) {14 c := NewCtx(t)15 defer c.Close()16 build := testBuild(1)17 c.client2.UploadBuild(build)18 crash := testCrash(build, 1)19 c.client2.ReportCrash(crash)20 c.client2.pollEmailBug()21 // No repro - no bisection.22 pollResp := c.client2.pollJobs(build.Manager)23 c.expectEQ(pollResp.ID, "")24 // Now upload 4 crashes with repros.25 crash2 := testCrashWithRepro(build, 2)26 c.client2.ReportCrash(crash2)27 msg2 := c.client2.pollEmailBug()28 // This is later, so will be bisected before the previous crash.29 c.advanceTime(time.Hour)30 crash3 := testCrashWithRepro(build, 3)31 c.client2.ReportCrash(crash3)32 c.client2.pollEmailBug()33 // This does not have C repro, so will be bisected after the previous ones.34 c.advanceTime(time.Hour)35 crash4 := testCrashWithRepro(build, 4)36 crash4.Title = "skip reporting2 with repro"37 crash4.ReproC = nil38 c.client2.ReportCrash(crash4)39 msg4 := c.client2.pollEmailBug()40 // This is from a different manager, so won't be bisected.41 c.advanceTime(time.Hour)42 build2 := testBuild(2)43 c.client2.UploadBuild(build2)44 crash5 := testCrashWithRepro(build2, 5)45 c.client2.ReportCrash(crash5)46 c.client2.pollEmailBug()47 pollResp = c.client2.pollJobs(build.Manager)48 c.expectNE(pollResp.ID, "")49 c.expectEQ(pollResp.Type, dashapi.JobBisectCause)50 c.expectEQ(pollResp.Manager, build.Manager)51 c.expectEQ(pollResp.KernelConfig, build.KernelConfig)52 c.expectEQ(pollResp.SyzkallerCommit, build.SyzkallerCommit)53 c.expectEQ(pollResp.ReproOpts, []byte("repro opts 3"))54 c.expectEQ(pollResp.ReproSyz, []byte("syncfs(3)"))55 c.expectEQ(pollResp.ReproC, []byte("int main() { return 3; }"))56 // Since we did not reply, we should get the same response.57 c.advanceTime(5 * 24 * time.Hour)58 pollResp2 := c.client2.pollJobs(build.Manager)59 c.expectEQ(pollResp, pollResp2)60 // Bisection failed with an error.61 done := &dashapi.JobDoneReq{62 ID: pollResp.ID,63 Log: []byte("bisect log 3"),64 Error: []byte("bisect error 3"),65 }66 c.expectOK(c.client2.JobDone(done))67 // Now we should get bisect for crash 2.68 pollResp = c.client2.pollJobs(build.Manager)69 c.expectNE(pollResp.ID, pollResp2.ID)70 c.expectEQ(pollResp.ReproOpts, []byte("repro opts 2"))71 // Bisection succeeded.72 jobID := pollResp.ID73 done = &dashapi.JobDoneReq{74 ID: jobID,75 Build: *build,76 Log: []byte("bisect log 2"),77 CrashTitle: "bisect crash title",78 CrashLog: []byte("bisect crash log"),79 CrashReport: []byte("bisect crash report"),80 Commits: []dashapi.Commit{81 {82 Hash: "36e65cb4a0448942ec316b24d60446bbd5cc7827",83 Title: "kernel: add a bug",84 Author: "author@kernel.org",85 AuthorName: "Author Kernelov",86 CC: []string{87 "reviewer1@kernel.org", "\"Reviewer2\" <reviewer2@kernel.org>",88 // These must be filtered out:89 "syzbot@testapp.appspotmail.com",90 "syzbot+1234@testapp.appspotmail.com",91 "\"syzbot\" <syzbot+1234@testapp.appspotmail.com>",92 },93 Date: time.Date(2000, 2, 9, 4, 5, 6, 7, time.UTC),94 },95 },96 }97 done.Build.ID = jobID98 c.expectOK(c.client2.JobDone(done))99 _, extBugID, err := email.RemoveAddrContext(msg2.Sender)100 c.expectOK(err)101 _, dbCrash, _ := c.loadBug(extBugID)102 reproSyzLink := externalLink(c.ctx, textReproSyz, dbCrash.ReproSyz)103 reproCLink := externalLink(c.ctx, textReproC, dbCrash.ReproC)104 dbJob, dbBuild, dbJobCrash := c.loadJob(jobID)105 kernelConfigLink := externalLink(c.ctx, textKernelConfig, dbBuild.KernelConfig)106 bisectCrashReportLink := externalLink(c.ctx, textCrashReport, dbJob.CrashReport)107 bisectCrashLogLink := externalLink(c.ctx, textCrashLog, dbJob.CrashLog)108 bisectLogLink := externalLink(c.ctx, textLog, dbJob.Log)109 crashLogLink := externalLink(c.ctx, textCrashLog, dbJobCrash.Log)110 {111 msg := c.pollEmailBug()112 // Not mailed to commit author/cc because !MailMaintainers.113 c.expectEQ(msg.To, []string{"test@syzkaller.com"})114 c.expectEQ(msg.Subject, crash2.Title)115 c.expectEQ(len(msg.Attachments), 0)116 c.expectEQ(msg.Body, fmt.Sprintf(`syzbot has bisected this bug to:117commit 36e65cb4a0448942ec316b24d60446bbd5cc7827118Author: Author Kernelov <author@kernel.org>119Date: Wed Feb 9 04:05:06 2000 +0000120 kernel: add a bug121bisection log: %[2]v122start commit: 11111111 kernel_commit_title1123git tree: repo1 branch1124final crash: %[3]v125console output: %[4]v126kernel config: %[5]v127dashboard link: https://testapp.appspot.com/bug?extid=%[1]v128syz repro: %[6]v129C reproducer: %[7]v130Reported-by: syzbot+%[1]v@testapp.appspotmail.com131Fixes: 36e65cb4a044 ("kernel: add a bug")132For information about bisection process see: https://goo.gl/tpsmEJ#bisection133`, extBugID, bisectLogLink, bisectCrashReportLink, bisectCrashLogLink, kernelConfigLink, reproSyzLink, reproCLink))134 syzRepro := []byte(fmt.Sprintf("%s#%s\n%s", syzReproPrefix, crash2.ReproOpts, crash2.ReproSyz))135 c.checkURLContents(bisectLogLink, []byte("bisect log 2"))136 c.checkURLContents(bisectCrashReportLink, []byte("bisect crash report"))137 c.checkURLContents(bisectCrashLogLink, []byte("bisect crash log"))138 c.checkURLContents(kernelConfigLink, []byte("config1"))139 c.checkURLContents(reproSyzLink, syzRepro)140 c.checkURLContents(reproCLink, crash2.ReproC)141 }142 // The next reporting must get bug report with bisection results.143 c.incomingEmail(msg2.Sender, "#syz upstream")144 {145 msg := c.pollEmailBug()146 _, extBugID2, err := email.RemoveAddrContext(msg.Sender)147 c.expectOK(err)148 c.expectEQ(msg.To, []string{149 "author@kernel.org",150 "bugs@syzkaller.com",151 "default@maintainers.com",152 "reviewer1@kernel.org",153 "reviewer2@kernel.org",154 })155 c.expectEQ(msg.Subject, crash2.Title)156 c.expectEQ(msg.Body, fmt.Sprintf(`Hello,157syzbot found the following crash on:158HEAD commit: 11111111 kernel_commit_title1159git tree: repo1 branch1160console output: %[2]v161kernel config: %[3]v162dashboard link: https://testapp.appspot.com/bug?extid=%[1]v163compiler: compiler1164syz repro: %[4]v165C reproducer: %[5]v166CC: [author@kernel.org reviewer1@kernel.org reviewer2@kernel.org]167The bug was bisected to:168commit 36e65cb4a0448942ec316b24d60446bbd5cc7827169Author: Author Kernelov <author@kernel.org>170Date: Wed Feb 9 04:05:06 2000 +0000171 kernel: add a bug172bisection log: %[6]v173final crash: %[7]v174console output: %[8]v175IMPORTANT: if you fix the bug, please add the following tag to the commit:176Reported-by: syzbot+%[1]v@testapp.appspotmail.com177Fixes: 36e65cb4a044 ("kernel: add a bug")178report2179---180This bug is generated by a bot. It may contain errors.181See https://goo.gl/tpsmEJ for more information about syzbot.182syzbot engineers can be reached at syzkaller@googlegroups.com.183syzbot will keep track of this bug report. See:184https://goo.gl/tpsmEJ#status for how to communicate with syzbot.185For information about bisection process see: https://goo.gl/tpsmEJ#bisection186syzbot can test patches for this bug, for details see:187https://goo.gl/tpsmEJ#testing-patches`,188 extBugID2, crashLogLink, kernelConfigLink, reproSyzLink, reproCLink,189 bisectLogLink, bisectCrashReportLink, bisectCrashLogLink))190 }191 // Crash 4 is bisected in reporting with MailMaintainers.192 // It also skipped second reporting because of the title.193 c.incomingEmail(msg4.Sender, "#syz upstream")194 msg4 = c.pollEmailBug()195 c.expectEQ(msg4.To, []string{196 "bugs2@syzkaller.com",197 "default2@maintainers.com",198 })199 pollResp = c.client2.pollJobs(build.Manager)200 // Bisection succeeded.201 jobID = pollResp.ID202 done = &dashapi.JobDoneReq{203 ID: jobID,204 Build: *build,205 Log: []byte("bisect log 4"),206 CrashTitle: "bisect crash title 4",207 CrashLog: []byte("bisect crash log 4"),208 CrashReport: []byte("bisect crash report 4"),209 Commits: []dashapi.Commit{210 {211 Hash: "36e65cb4a0448942ec316b24d60446bbd5cc7827",212 Title: "kernel: add a bug",213 Author: "author@kernel.org",214 AuthorName: "Author Kernelov",215 CC: []string{216 "reviewer1@kernel.org", "\"Reviewer2\" <reviewer2@kernel.org>",217 // These must be filtered out:218 "syzbot@testapp.appspotmail.com",219 "syzbot+1234@testapp.appspotmail.com",220 "\"syzbot\" <syzbot+1234@testapp.appspotmail.com>",221 },222 Date: time.Date(2000, 2, 9, 4, 5, 6, 7, time.UTC),223 },224 },225 }226 done.Build.ID = jobID227 c.expectOK(c.client2.JobDone(done))228 {229 msg := c.pollEmailBug()230 c.expectEQ(msg.Subject, crash4.Title)231 c.expectEQ(msg.To, []string{232 "author@kernel.org",233 "bugs2@syzkaller.com",234 "default2@maintainers.com",235 "reviewer1@kernel.org",236 "reviewer2@kernel.org",237 })238 }239 // No more bisection jobs.240 pollResp = c.client2.pollJobs(build.Manager)241 c.expectEQ(pollResp.ID, "")242}243func TestBisectCauseInconclusive(t *testing.T) {244 c := NewCtx(t)245 defer c.Close()246 build := testBuild(1)247 c.client2.UploadBuild(build)248 crash := testCrashWithRepro(build, 1)249 c.client2.ReportCrash(crash)250 msg := c.client2.pollEmailBug()251 pollResp := c.client2.pollJobs(build.Manager)252 jobID := pollResp.ID253 done := &dashapi.JobDoneReq{254 ID: jobID,255 Build: *build,256 Log: []byte("bisect log"),257 Commits: []dashapi.Commit{258 {259 Hash: "111111111111111111111111",260 Title: "kernel: break build",261 Author: "hacker@kernel.org",262 AuthorName: "Hacker Kernelov",263 CC: []string{"reviewer1@kernel.org", "reviewer2@kernel.org"},264 Date: time.Date(2000, 2, 9, 4, 5, 6, 7, time.UTC),265 },266 {267 Hash: "222222222222222222222222",268 Title: "kernel: now add a bug to the broken build",269 Author: "author@kernel.org",270 AuthorName: "Author Kernelov",271 CC: []string{"reviewer3@kernel.org", "reviewer4@kernel.org"},272 Date: time.Date(2001, 2, 9, 4, 5, 6, 7, time.UTC),273 },274 },275 }276 done.Build.ID = jobID277 c.expectOK(c.client2.JobDone(done))278 _, extBugID, err := email.RemoveAddrContext(msg.Sender)279 c.expectOK(err)280 _, dbCrash, _ := c.loadBug(extBugID)281 reproSyzLink := externalLink(c.ctx, textReproSyz, dbCrash.ReproSyz)282 reproCLink := externalLink(c.ctx, textReproC, dbCrash.ReproC)283 dbJob, dbBuild, dbJobCrash := c.loadJob(jobID)284 kernelConfigLink := externalLink(c.ctx, textKernelConfig, dbBuild.KernelConfig)285 bisectLogLink := externalLink(c.ctx, textLog, dbJob.Log)286 crashLogLink := externalLink(c.ctx, textCrashLog, dbJobCrash.Log)287 {288 msg := c.pollEmailBug()289 // Not mailed to commit author/cc because !MailMaintainers.290 c.expectEQ(msg.To, []string{"test@syzkaller.com"})291 c.expectEQ(msg.Subject, crash.Title)292 c.expectEQ(len(msg.Attachments), 0)293 c.expectEQ(msg.Body, fmt.Sprintf(`Bisection is inconclusive: the first bad commit could be any of:29411111111 kernel: break build29522222222 kernel: now add a bug to the broken build296bisection log: %[2]v297start commit: 11111111 kernel_commit_title1298git tree: repo1 branch1299kernel config: %[3]v300dashboard link: https://testapp.appspot.com/bug?extid=%[1]v301syz repro: %[4]v302C reproducer: %[5]v303For information about bisection process see: https://goo.gl/tpsmEJ#bisection304`, extBugID, bisectLogLink, kernelConfigLink, reproSyzLink, reproCLink))305 }306 // The next reporting must get bug report with bisection results.307 c.incomingEmail(msg.Sender, "#syz upstream")308 {309 msg := c.pollEmailBug()310 _, extBugID2, err := email.RemoveAddrContext(msg.Sender)311 c.expectOK(err)312 c.expectEQ(msg.To, []string{313 "bugs@syzkaller.com",314 "default@maintainers.com",315 })316 c.expectEQ(msg.Body, fmt.Sprintf(`Hello,317syzbot found the following crash on:318HEAD commit: 11111111 kernel_commit_title1319git tree: repo1 branch1320console output: %[2]v321kernel config: %[3]v322dashboard link: https://testapp.appspot.com/bug?extid=%[1]v323compiler: compiler1324syz repro: %[4]v325C reproducer: %[5]v326Bisection is inconclusive: the first bad commit could be any of:32711111111 kernel: break build32822222222 kernel: now add a bug to the broken build329bisection log: %[6]v330IMPORTANT: if you fix the bug, please add the following tag to the commit:331Reported-by: syzbot+%[1]v@testapp.appspotmail.com332report1333---334This bug is generated by a bot. It may contain errors.335See https://goo.gl/tpsmEJ for more information about syzbot.336syzbot engineers can be reached at syzkaller@googlegroups.com.337syzbot will keep track of this bug report. See:338https://goo.gl/tpsmEJ#status for how to communicate with syzbot.339For information about bisection process see: https://goo.gl/tpsmEJ#bisection340syzbot can test patches for this bug, for details see:341https://goo.gl/tpsmEJ#testing-patches`,342 extBugID2, crashLogLink, kernelConfigLink, reproSyzLink, reproCLink, bisectLogLink))343 }344}345func TestBisectCauseAncient(t *testing.T) {346 c := NewCtx(t)347 defer c.Close()348 build := testBuild(1)349 c.client2.UploadBuild(build)350 crash := testCrashWithRepro(build, 1)351 c.client2.ReportCrash(crash)352 msg := c.client2.pollEmailBug()353 pollResp := c.client2.pollJobs(build.Manager)354 jobID := pollResp.ID355 done := &dashapi.JobDoneReq{356 ID: jobID,357 Build: *build,358 Log: []byte("bisect log"),359 CrashTitle: "bisect crash title",360 CrashLog: []byte("bisect crash log"),361 CrashReport: []byte("bisect crash report"),362 }363 done.Build.ID = jobID364 c.expectOK(c.client2.JobDone(done))365 _, extBugID, err := email.RemoveAddrContext(msg.Sender)366 c.expectOK(err)367 _, dbCrash, _ := c.loadBug(extBugID)368 reproSyzLink := externalLink(c.ctx, textReproSyz, dbCrash.ReproSyz)369 reproCLink := externalLink(c.ctx, textReproC, dbCrash.ReproC)370 dbJob, dbBuild, dbJobCrash := c.loadJob(jobID)371 bisectCrashReportLink := externalLink(c.ctx, textCrashReport, dbJob.CrashReport)372 bisectCrashLogLink := externalLink(c.ctx, textCrashLog, dbJob.CrashLog)373 kernelConfigLink := externalLink(c.ctx, textKernelConfig, dbBuild.KernelConfig)374 bisectLogLink := externalLink(c.ctx, textLog, dbJob.Log)375 crashLogLink := externalLink(c.ctx, textCrashLog, dbJobCrash.Log)376 {377 msg := c.pollEmailBug()378 // Not mailed to commit author/cc because !MailMaintainers.379 c.expectEQ(msg.To, []string{"test@syzkaller.com"})380 c.expectEQ(msg.Subject, crash.Title)381 c.expectEQ(len(msg.Attachments), 0)382 c.expectEQ(msg.Body, fmt.Sprintf(`Bisection is inconclusive: the bug happens on the oldest tested release.383bisection log: %[2]v384start commit: 11111111 kernel_commit_title1385git tree: repo1 branch1386final crash: %[3]v387console output: %[4]v388kernel config: %[5]v389dashboard link: https://testapp.appspot.com/bug?extid=%[1]v390syz repro: %[6]v391C reproducer: %[7]v392For information about bisection process see: https://goo.gl/tpsmEJ#bisection393`, extBugID, bisectLogLink, bisectCrashReportLink, bisectCrashLogLink,394 kernelConfigLink, reproSyzLink, reproCLink))395 }396 // The next reporting must get bug report with bisection results.397 c.incomingEmail(msg.Sender, "#syz upstream")398 {399 msg := c.pollEmailBug()400 _, extBugID2, err := email.RemoveAddrContext(msg.Sender)401 c.expectOK(err)402 c.expectEQ(msg.To, []string{403 "bugs@syzkaller.com",404 "default@maintainers.com",405 })406 c.expectEQ(msg.Body, fmt.Sprintf(`Hello,407syzbot found the following crash on:408HEAD commit: 11111111 kernel_commit_title1409git tree: repo1 branch1410console output: %[2]v411kernel config: %[3]v412dashboard link: https://testapp.appspot.com/bug?extid=%[1]v413compiler: compiler1414syz repro: %[4]v415C reproducer: %[5]v416Bisection is inconclusive: the bug happens on the oldest tested release.417bisection log: %[6]v418final crash: %[7]v419console output: %[8]v420IMPORTANT: if you fix the bug, please add the following tag to the commit:421Reported-by: syzbot+%[1]v@testapp.appspotmail.com422report1423---424This bug is generated by a bot. It may contain errors.425See https://goo.gl/tpsmEJ for more information about syzbot.426syzbot engineers can be reached at syzkaller@googlegroups.com.427syzbot will keep track of this bug report. See:428https://goo.gl/tpsmEJ#status for how to communicate with syzbot.429For information about bisection process see: https://goo.gl/tpsmEJ#bisection430syzbot can test patches for this bug, for details see:431https://goo.gl/tpsmEJ#testing-patches`,432 extBugID2, crashLogLink, kernelConfigLink, reproSyzLink, reproCLink,433 bisectLogLink, bisectCrashReportLink, bisectCrashLogLink))434 }435}436func TestBisectCauseExternal(t *testing.T) {437 c := NewCtx(t)438 defer c.Close()439 build := testBuild(1)440 c.client.UploadBuild(build)441 crash := testCrashWithRepro(build, 1)442 c.client.ReportCrash(crash)443 rep := c.client.pollBug()444 pollResp := c.client.pollJobs(build.Manager)445 jobID := pollResp.ID446 done := &dashapi.JobDoneReq{447 ID: jobID,448 Build: *build,449 Log: []byte("bisect log"),450 Commits: []dashapi.Commit{451 {452 Hash: "111111111111111111111111",453 Title: "kernel: break build",454 Author: "hacker@kernel.org",455 AuthorName: "Hacker Kernelov",456 CC: []string{"reviewer1@kernel.org", "reviewer2@kernel.org"},457 Date: time.Date(2000, 2, 9, 4, 5, 6, 7, time.UTC),458 },459 },460 }461 done.Build.ID = jobID462 c.expectOK(c.client2.JobDone(done))463 resp, _ := c.client.ReportingPollBugs("test")464 c.expectEQ(len(resp.Reports), 1)465 // Still reported because we did not ack.466 bisect := c.client.pollBug()467 // pollBug acks, must not be reported after that.468 c.client.pollBugs(0)469 c.expectEQ(bisect.Type, dashapi.ReportBisectCause)470 c.expectEQ(bisect.Title, rep.Title)471}472func TestBisectCauseReproSyz(t *testing.T) {473 c := NewCtx(t)474 defer c.Close()475 build := testBuild(1)476 c.client2.UploadBuild(build)477 crash := testCrashWithRepro(build, 1)478 crash.ReproC = nil479 c.client2.ReportCrash(crash)480 pollResp := c.client2.pollJobs(build.Manager)481 jobID := pollResp.ID482 done := &dashapi.JobDoneReq{483 ID: jobID,484 Build: *build,485 Log: []byte("bisect log"),486 CrashTitle: "bisect crash title",487 CrashLog: []byte("bisect crash log"),488 }489 done.Build.ID = jobID490 c.expectOK(c.client2.JobDone(done))491 crash.ReproC = []byte("int main")492 c.client2.ReportCrash(crash)493 msg := c.client2.pollEmailBug()494 if !strings.Contains(msg.Body, "syzbot found the following crash") {495 t.Fatalf("wrong email header:\n%v", msg.Body)496 }497 if !strings.Contains(msg.Body, "Bisection is inconclusive") {498 t.Fatalf("report does not contain bisection results:\n%v", msg.Body)499 }500}501func TestBisectCauseReproSyz2(t *testing.T) {502 c := NewCtx(t)503 defer c.Close()504 build := testBuild(1)505 c.client2.UploadBuild(build)506 crash := testCrashWithRepro(build, 1)507 crash.ReproC = nil508 c.client2.ReportCrash(crash)509 pollResp := c.client2.pollJobs(build.Manager)510 jobID := pollResp.ID511 done := &dashapi.JobDoneReq{512 ID: jobID,513 Build: *build,514 Log: []byte("bisect log"),515 CrashTitle: "bisect crash title",...
TestBisectCause
Using AI Code Generation
1import (2func main() {3 fmt.Println("Hello, playground")4 test := TestBisectCause{TestName: "test1"}5 test.AddCause("cause1")6 test.AddCause("cause2")7 test.AddCause("cause3")8 test.AddCause("cause4")9 test.AddCause("cause5")10 test.AddCause("cause6")11 test.AddCause("cause7")12 test.AddCause("cause8")13 test.AddCause("cause9")14 test.AddCause("cause10")15 test.AddCause("cause11")16 test.AddCause("cause12")17 test.AddCause("cause13")18 test.AddCause("cause14")19 test.AddCause("cause15")20 test.AddCause("cause16")21 test.AddCause("cause17")22 test.AddCause("cause18")23 test.AddCause("cause19")24 test.AddCause("cause20")25 test.AddCause("cause21")26 test.AddCause("cause22")27 test.AddCause("cause23")28 test.AddCause("cause24")29 test.AddCause("cause25")30 test.AddCause("cause26")31 test.AddCause("cause27")32 test.AddCause("cause28")33 test.AddCause("cause29")34 test.AddCause("cause30")35 test.AddCause("cause31")36 test.AddCause("cause32")37 test.AddCause("cause33")38 test.AddCause("cause34")39 test.AddCause("cause35")40 test.AddCause("cause36")41 test.AddCause("cause37")42 test.AddCause("cause38")43 test.AddCause("cause39")44 test.AddCause("cause40")45 test.AddCause("cause41")46 test.AddCause("cause42")47 test.AddCause("cause43")48 test.AddCause("cause44")49 test.AddCause("cause45")50 test.AddCause("cause46")51 test.AddCause("cause47")52 test.AddCause("cause48")53 test.AddCause("cause49")54 test.AddCause("cause50")55 test.AddCause("cause51")56 test.AddCause("cause52")57 test.AddCause("cause53")58 test.AddCause("cause54")59 test.AddCause("cause55")60 test.AddCause("cause56")
Learn to execute automation testing from scratch with LambdaTest Learning Hub. Right from setting up the prerequisites to run your first automation test, to following best practices and diving deeper into advanced test scenarios. LambdaTest Learning Hubs compile a list of step-by-step guides to help you be proficient with different test automation frameworks i.e. Selenium, Cypress, TestNG etc.
You could also refer to video tutorials over LambdaTest YouTube channel to get step by step demonstration from industry experts.
Get 100 minutes of automation test minutes FREE!!