সেলেনিয়াম ওয়েবড্রাইভার: জাভাস্ক্রিপ্ট লোড করার জন্য জটিল পৃষ্ঠার জন্য অপেক্ষা করুন


104

সেলেনিয়ামের সাথে পরীক্ষা করার জন্য আমার একটি ওয়েব অ্যাপ্লিকেশন রয়েছে। পৃষ্ঠা লোডটিতে প্রচুর জাভাস্ক্রিপ্ট চলছে।
এই জাভাস্ক্রিপ্ট কোডটি তেমন ভাল লেখা হয় নি তবে আমি কিছুই পরিবর্তন করতে পারি না। সুতরাং findElement()পদ্ধতির সাথে ডিওমে উপস্থিত থাকতে কোনও উপাদানটির জন্য অপেক্ষা করা কোনও বিকল্প নয়।
কোনও পৃষ্ঠা লোড হওয়ার জন্য অপেক্ষা করার জন্য আমি জাভাতে একটি জেনেরিক ফাংশন তৈরি করতে চাই, একটি সম্ভাব্য সমাধান হ'ল:

  • একটি জাভাস্ক্রিপ্ট স্ক্রিপ্ট ফর্ম ওয়েব ড্রাইভ চালান document.body.innerHTMLএবং একটি স্ট্রিং ভেরিয়েবলের ফলাফল সংরক্ষণ করুন body
  • bodyএর পূর্ববর্তী সংস্করণটির সাথে ভেরিয়েবলের তুলনা করুন body। যদি তারা একই হয় তবে ইনক্রিমেন্টকে একটি কাউন্টার notChangedCountসেট করুন অন্যথায় notChangedCountশূন্যতে সেট করুন।
  • একটি লিট সময় অপেক্ষা করুন (উদাহরণস্বরূপ 50 এমএস)।
  • যদি পৃষ্ঠাটি কিছু সময়ের জন্য পরিবর্তিত হয় না (উদাহরণস্বরূপ 500 এমএস) notChangedCount >= 10তবে লুপটি অন্যথায় প্রথম ধাপে প্রস্থান করুন।

আপনি কি মনে করেন এটি একটি কার্যকর সমাধান?


FindElement () অপেক্ষা করে না - এর সাথে আপনি কী বোঝাতে চাইছেন?
রোস্টিস্লাভ ম্যাটেল

4
findElementকোনও উপাদান উপলভ্য হওয়ার জন্য অপেক্ষা করে, তবে কখনও কখনও জাভাস্ক্রিপ্ট কোড সম্পূর্ণরূপে আরম্ভ করার আগে উপাদানটি উপলব্ধ থাকে, এজন্য এটি কোনও বিকল্প নয়।
psadac

আমি এটি ভুলে গেছি - আমি ওয়েবড্রাইভারওয়েট এবং এক্সপেক্টেড কনডিশনটি এটি আরও নমনীয় using
রোস্টিস্লাভ ম্যাটেল

উত্তর:


73

যদি কেউ আসলে একটি সাধারণ এবং সর্বদা প্রযোজ্য উত্তর জানত তবে এটি যুগ যুগ আগে সর্বত্র কার্যকর করা হত এবং আমাদের জীবনকে আরও সহজ করে দিত।

আপনি করতে পারেন এমন অনেকগুলি জিনিস রয়েছে তবে তাদের প্রত্যেকটিরই একটি সমস্যা রয়েছে:

  1. হিসাবে অশ্বিন প্রভু বলেন, তাহলে আপনারা স্ক্রিপ্ট ভাল জানেন, আপনি তার আচরণ পালন করা এবং তার ভেরিয়েবল কিছু ট্র্যাক করতে পারেন windowবা documentএই সমাধান ইত্যাদি অবশ্য সবার জন্য নয় এবং আপনার দ্বারা এবং শুধুমাত্র একটি সীমিত সেটে শুধুমাত্র ব্যবহার করা যেতে পারে পৃষ্ঠা।

  2. এইচটিএমএল কোডটি পর্যবেক্ষণ করে এবং এটি কিছু সময়ের জন্য পরিবর্তিত হয়েছে কিনা তা আপনার সমাধানটি খারাপ নয় (এছাড়াও, আসল এবং সম্পাদিত এইচটিএমএল সরাসরি দ্বারা পাওয়ার একটি পদ্ধতি রয়েছেWebDriver ) তবে:

    • প্রকৃতপক্ষে কোনও পৃষ্ঠা চাপিয়ে দিতে এটি দীর্ঘ সময় নেয় এবং পরীক্ষাটি উল্লেখযোগ্যভাবে দীর্ঘায়িত করতে পারে।
    • সঠিক বিরতি কী তা আপনি কখনই জানেন না। স্ক্রিপ্ট পারে কিছু বড় বেশি 500 MS লাগে ডাউনলোড করার করা হবে। আমাদের সংস্থার অভ্যন্তরীণ পৃষ্ঠায় বেশ কয়েকটি স্ক্রিপ্ট রয়েছে যা আইইতে কয়েক সেকেন্ড সময় নেয়। আপনার কম্পিউটার অস্থায়ীভাবে সংস্থানগুলিতে সংক্ষিপ্ত হতে পারে - বলুন যে কোনও অ্যান্টিভাইরাস আপনার সিপিইউ পুরোপুরি কাজ করবে, তবে 500 এমএস কোনও ননকম্পলিক্স স্ক্রিপ্টের জন্য খুব ছোটও হতে পারে।
    • কিছু স্ক্রিপ্ট কখনও করা হয় না। তারা কিছুটা দেরি করে ( setTimeout()) ডেকে নিজেকে পুনরায় ফোন করে এবং বারবার কাজ করে এবং সম্ভবত তারা যখনই চালায় তখন এইচটিএমএল পরিবর্তন করতে পারে। গুরুতরভাবে, প্রতিটি "ওয়েব 2.0" পৃষ্ঠা এটি করে। এমনকি স্ট্যাক ওভারফ্লো। আপনি ব্যবহৃত সর্বাধিক সাধারণ পদ্ধতিগুলি ওভাররাইট করতে এবং স্ক্রিপ্টগুলি সেগুলি হিসাবে সম্পূর্ণ হিসাবে ব্যবহার করে তা বিবেচনা করতে পারেন, তবে ... আপনি নিশ্চিত হতে পারবেন না।
    • যদি স্ক্রিপ্টটি এইচটিএমএল পরিবর্তন ছাড়া অন্য কিছু করে? এটি হাজার হাজার জিনিস করতে পারে, কেবল কিছু innerHTMLমজা নয় fun
  3. এটিতে আপনাকে সহায়তা করার জন্য সরঞ্জামগুলি রয়েছে। যেমন অগ্রগতি শ্রোতাদের একসঙ্গে সঙ্গে nsIWebProgressListener এবং কিছু অন্যদের। এটির জন্য ব্রাউজারের সমর্থনটি ভয়াবহ। ফায়ারফক্স এফএফ 4 এর পরে এটি সমর্থন করার চেষ্টা করতে শুরু করে (এখনও বিকশিত হয়), আইই 9-র IE9 এর প্রাথমিক সমর্থন রয়েছে।

এবং আমার ধারণা আমি শীঘ্রই অন্য একটি ত্রুটিযুক্ত সমাধান নিয়ে আসতে পারব। সত্যটি হ'ল - চিরস্থায়ী স্ক্রিপ্টগুলি তাদের কাজ করার কারণে "এখন পৃষ্ঠাটি সম্পূর্ণ হয়েছে" বলার কোনও নির্দিষ্ট উত্তর নেই। যিনি আপনাকে সর্বোত্তমভাবে পরিবেশন করেন তা চয়ন করুন তবে এর ত্রুটিগুলি থেকে সাবধান থাকুন।


31

ধন্যবাদ আশ্বিন!

আমার ক্ষেত্রে আমার কিছু উপাদানগুলির জন্য একটি jquery প্লাগইন সম্পাদনের জন্য অপেক্ষা করা উচিত .. বিশেষত "qtip"

আপনার ইঙ্গিত ভিত্তিতে, এটি আমার জন্য নিখুঁতভাবে কাজ করেছে:

wait.until( new Predicate<WebDriver>() {
            public boolean apply(WebDriver driver) {
                return ((JavascriptExecutor)driver).executeScript("return document.readyState").equals("complete");
            }
        }
    );

দ্রষ্টব্য: আমি ওয়েবড্রাইভার 2 ব্যবহার করছি


4
এটা আমার জন্য খুব ভাল কাজ করে। আমার ক্ষেত্রে, পৃষ্ঠাটি লোডিং শেষ হওয়ার ঠিক পরে জাভাস্ক্রিপ্ট দ্বারা একটি উপাদান সংশোধন করা হয়েছিল এবং সেলেনিয়াম সেই স্পষ্টভাবে অপেক্ষা করছে না।
Noxxys

4
প্রিডিকেট কোথা থেকে আসে? কোন আমদানি ??
আমাদো সালাদিনো 31'19

@ আমাদোসালাদিনো "আমদানি com.google.common.base.Predicate;" গুগল লাইব পেয়ারা -15.0 লিঙ্ক থেকে: mvnrepository.com/artifact/com.google.guava/guava/15.0 নতুন সংস্করণ আছে 27.0 আপনি এটি চেষ্টা করতে পারেন!
এডুয়ার্ডো ফ্যাব্রিকিও

26

লোড শেষ করার জন্য আপনাকে জাভাস্ক্রিপ্ট এবং jQuery অপেক্ষা করতে হবে। যদি চেক করতে জাভাস্ক্রিপ্ট সম্পাদন jQuery.activeহয় 0এবং document.readyStateহয় completeযার মানে জাতীয় এবং jQuery লোড সম্পূর্ণ হলে,।

public boolean waitForJStoLoad() {

    WebDriverWait wait = new WebDriverWait(driver, 30);

    // wait for jQuery to load
    ExpectedCondition<Boolean> jQueryLoad = new ExpectedCondition<Boolean>() {
      @Override
      public Boolean apply(WebDriver driver) {
        try {
          return ((Long)executeJavaScript("return jQuery.active") == 0);
        }
        catch (Exception e) {
          return true;
        }
      }
    };

    // wait for Javascript to load
    ExpectedCondition<Boolean> jsLoad = new ExpectedCondition<Boolean>() {
      @Override
      public Boolean apply(WebDriver driver) {
        return executeJavaScript("return document.readyState")
            .toString().equals("complete");
      }
    };

  return wait.until(jQueryLoad) && wait.until(jsLoad);
}

4
এটি প্রতিটি পরিস্থিতিতে কাজ করবে কিনা তা নিশ্চিত নয় , তবে এটি আমার ব্যবহারের ক্ষেত্রে একটি ট্রিট কাজ করে
DaveH

4
এটি আমার পক্ষেও কার্যকর তবে একটি কৌতূহলপূর্ণ অংশ রয়েছে: ধরা যাক আপনার পৃষ্ঠাটি ইতিমধ্যে লোড হয়েছে। আপনি যদি কোনও উপাদানের সাথে ইন্টারঅ্যাক্ট করেন [উদাহরণস্বরূপ একটি ক্লিক করুন () বা এটিতে কিছু কী প্রেরণ করুন] এবং তারপরে আপনার পৃষ্ঠাটি প্রক্রিয়াকরণ শেষ হয়ে গেলে আপনার একটি বিলম্ব যোগ করতে হবে তা পরীক্ষা করতে চান: উদাহরণস্বরূপ (ক্লিক করুন), ঘুম (০.০ সেকেন্ড) ), অবধি অপেক্ষা করুন (রেডিস্টেট = 'সম্পূর্ণ' এবং jQuery.active == 0)। আপনি যদি ঘুম যোগ না করেন, তবে আইকোয়ারি পরীক্ষার সময় সক্রিয় হবে না! (এটি জানতে আমার কয়েক ঘন্টা সময় লেগেছে, তাই আমি এটি ভাগ করে নেওয়ার চিন্তা করেছি)
Fivos Vilanakis

document.readyState == 'complete' && jQuery.active == 0দুর্দান্ত কাজ করে কিন্তু প্রতিক্রিয়ার জন্য কি এরকম কিছু আছে? যেহেতু এই চেকগুলি এখনও ডেটা / উপাদান লোড করে প্রতিক্রিয়া দেখায় না?
Rain9333

10

জেএস লাইব্রেরি উইন্ডোতে কোনও সুপরিচিত চলক সংজ্ঞায়িত / আরম্ভ করতে পারে?

যদি তাই হয় আপনি ভেরিয়েবলটি প্রদর্শিত হওয়ার জন্য অপেক্ষা করতে পারেন। তুমি ব্যবহার করতে পার

((JavascriptExecutor)driver).executeScript(String script, Object... args)

এই অবস্থার জন্য পরীক্ষা করতে (যেমন কিছু window.SomeClass && window.SomeClass.variable != null:) এবং একটি বুলিয়ান true/false

এটিকে একটিতে মুড়ে ফেলুন WebDriverWaitএবং স্ক্রিপ্টটি ফিরে না আসা পর্যন্ত অপেক্ষা করুন true


8

যদি আপনাকে যা করার দরকার হয় উপাদানগুলির সাথে আলাপচারিতা করার আগে পৃষ্ঠায় এইচটিএমএল স্থিতিশীল হওয়ার জন্য অপেক্ষা করা হয়, আপনি পর্যায়ক্রমে ডমটি পোল করতে পারেন এবং ফলাফলগুলি তুলনা করতে পারেন, যদি প্রদত্ত পোলের সময়কালে ডিওএমগুলি একই হয় তবে আপনি সোনালী. তুলনা করার আগে আপনি সর্বাধিক অপেক্ষার সময় এবং পৃষ্ঠা নির্বাচনের মধ্যবর্তী সময়ের মধ্যে এই জাতীয় কিছু পাঠান। সহজ এবং কার্যকর।

public void waitForJavascript(int maxWaitMillis, int pollDelimiter) {
    double startTime = System.currentTimeMillis();
    while (System.currentTimeMillis() < startTime + maxWaitMillis) {
        String prevState = webDriver.getPageSource();
        Thread.sleep(pollDelimiter); // <-- would need to wrap in a try catch
        if (prevState.equals(webDriver.getPageSource())) {
            return;
        }
    }
}

4
আমি এখানে উল্লেখ করতে চাই যে আমি মাঝারি আকারের পৃষ্ঠাটি দু'বার পোল করার জন্য লগ করেছি, তার পরে জাভাতে এই স্ট্রিংগুলির তুলনা করুন এবং এটি 20 মাইলেরও বেশি সময় নিয়েছে।
TheFreddyKilo

4
প্রথমে আমি এটি একটি নোংরা সমাধান হিসাবে পেয়েছি, তবে এটি দুর্দান্ত কাজ করছে বলে মনে হচ্ছে এবং এতে ভেরিয়েবলের ক্লায়েন্টের দিক নির্ধারণ করা জড়িত না। একটি ক্যাভিট এমন একটি পৃষ্ঠা হতে পারে যা ক্রমাগত জাভাস্ক্রিপ্ট দ্বারা পরিবর্তন করা হচ্ছে (যেমন একটি জাভাস্ক্রিপ্ট ঘড়ি) তবে আমার এটি নেই তাই এটি কাজ করে!
পিটার

7

আমারও একই সমস্যা ছিল। এই সমাধানটি ওয়েবড্রাইভারডোকু থেকে আমার জন্য কাজ করে:

WebDriverWait wait = new WebDriverWait(driver, 10);
WebElement element = wait.until(ExpectedConditions.elementToBeClickable(By.id("someid")));

http://www.seleniumhq.org/docs/04_webdriver_advanced.jsp


ধন্যবাদ. লিঙ্কটিতে থাকা
কোডটি

4

নীচের কোডটি আমার ক্ষেত্রে পুরোপুরি কাজ করে - আমার পৃষ্ঠায় জটিল জাভা স্ক্রিপ্ট রয়েছে

public void checkPageIsReady() {

  JavascriptExecutor js = (JavascriptExecutor)driver;


  //Initially bellow given if condition will check ready state of page.
  if (js.executeScript("return document.readyState").toString().equals("complete")){ 
   System.out.println("Page Is loaded.");
   return; 
  } 

  //This loop will rotate for 25 times to check If page Is ready after every 1 second.
  //You can replace your value with 25 If you wants to Increase or decrease wait time.
  for (int i=0; i<25; i++){ 
   try {
    Thread.sleep(1000);
    }catch (InterruptedException e) {} 
   //To check page ready state.
   if (js.executeScript("return document.readyState").toString().equals("complete")){ 
    break; 
   }   
  }
 }

উত্স - সেলেনিয়াম ওয়েবড্রাইভারে লোড করার জন্য / প্রস্তুত পৃষ্ঠা কীভাবে অপেক্ষা করা যায়


4
আপনার এই লুপগুলির পরিবর্তে সেলেনিয়াম
ওয়েটগুলি

4

পৃষ্ঠায় কোনও উপাদান খুঁজে পাওয়ার আগে পৃষ্ঠাটি লোড হয়েছে কিনা তা পরীক্ষা করতে দুটি শর্ত ব্যবহার করা যেতে পারে:

WebDriverWait wait = new WebDriverWait(driver, 50);

নীচে রেডিস্টেট ব্যবহার করা পৃষ্ঠা লোড হওয়া পর্যন্ত অপেক্ষা করবে

wait.until((ExpectedCondition<Boolean>) wd ->
   ((JavascriptExecutor) wd).executeScript("return document.readyState").equals("complete"));

JQuery এর নীচে ডেটা লোড না হওয়া পর্যন্ত অপেক্ষা করা হবে

  int count =0;
            if((Boolean) executor.executeScript("return window.jQuery != undefined")){
                while(!(Boolean) executor.executeScript("return jQuery.active == 0")){
                    Thread.sleep(4000);
                    if(count>4)
                        break;
                    count++;
                }
            }

এই জাভাস্ক্রিপ্ট কোডের পরে ওয়েব-এলিমেন্টের সন্ধান করার চেষ্টা করুন।

WebElement we = wait.until(ExpectedConditions.presenceOfElementLocated(by));

4
সেলেনিয়াম এটি ডিফল্টরূপেও করে, এটি আপনার স্ক্রিপ্টে কিছু অতিরিক্ত কোড এক্সিকিউশন সময় যুক্ত করবে (অতিরিক্ত জিনিসগুলি লোড করার জন্য এটি যথেষ্ট সময় হতে পারে, তবে আবার তা নাও হতে পারে)
আর্দেসকো

2

আমি আমার বিকাশকারীদের একটি জাভাস্ক্রিপ্ট ভেরিয়েবল "isProcessing" তৈরি করতে বলেছিলাম যা আমি অ্যাক্সেস করতে পারি ("ae" অবজেক্টে) যা তারা সেট করে যখন জিনিসগুলি চলমান শুরু হয় এবং জিনিসগুলি হয়ে গেলে পরিষ্কার হয় clear তারপরে আমি এটিকে এমন একটি সঞ্চালকটিতে চালিত করি যা এটি কোনও পরিবর্তন ছাড়াই মোট 500 এমএসের জন্য পরপর পাঁচটি না পাওয়া পর্যন্ত এটি প্রতি 100 এমএস পরীক্ষা করে। যদি 30 সেকেন্ড উত্তীর্ণ হয় তবে আমি একটি ব্যতিক্রম ছুঁড়ে ফেলি কারণ এরপরে কিছু হওয়া উচিত ছিল। এটি সি # তে রয়েছে।

public static void WaitForDocumentReady(this IWebDriver driver)
{
    Console.WriteLine("Waiting for five instances of document.readyState returning 'complete' at 100ms intervals.");
    IJavaScriptExecutor jse = (IJavaScriptExecutor)driver;
    int i = 0; // Count of (document.readyState === complete) && (ae.isProcessing === false)
    int j = 0; // Count of iterations in the while() loop.
    int k = 0; // Count of times i was reset to 0.
    bool readyState = false;
    while (i < 5)
    {
        System.Threading.Thread.Sleep(100);
        readyState = (bool)jse.ExecuteScript("return ((document.readyState === 'complete') && (ae.isProcessing === false))");
        if (readyState) { i++; }
        else
        {
            i = 0;
            k++;
        }
        j++;
        if (j > 300) { throw new TimeoutException("Timeout waiting for document.readyState to be complete."); }
    }
    j *= 100;
    Console.WriteLine("Waited " + j.ToString() + " milliseconds. There were " + k + " resets.");
}

1

এটি সঠিকভাবে করতে, আপনাকে ব্যতিক্রমগুলি পরিচালনা করতে হবে।

আইফ্রেমের জন্য আমি কীভাবে অপেক্ষা করব তা এখানে। এটির জন্য আপনার JUnit পরীক্ষা ক্লাসটি রিমোট ওয়েবেড্রাইভারের উদাহরণটি পৃষ্ঠা পৃষ্ঠাতে পাস করতে হবে:

public class IFrame1 extends LoadableComponent<IFrame1> {

    private RemoteWebDriver driver;

    @FindBy(id = "iFrame1TextFieldTestInputControlID" )
    public WebElement iFrame1TextFieldInput;

    @FindBy(id = "iFrame1TextFieldTestProcessButtonID" )
    public WebElement copyButton;

    public IFrame1( RemoteWebDriver drv ) {
        super();
        this.driver = drv;
        this.driver.switchTo().defaultContent();
        waitTimer(1, 1000);
        this.driver.switchTo().frame("BodyFrame1");
        LOGGER.info("IFrame1 constructor...");
    }

    @Override
    protected void isLoaded() throws Error {        
        LOGGER.info("IFrame1.isLoaded()...");
        PageFactory.initElements( driver, this );
        try {
            assertTrue( "Page visible title is not yet available.", driver
     .findElementByCssSelector("body form#webDriverUnitiFrame1TestFormID h1")
                    .getText().equals("iFrame1 Test") );
        } catch ( NoSuchElementException e) {
            LOGGER.info("No such element." );
            assertTrue("No such element.", false);
        }
    }

    @Override
    protected void load() {
        LOGGER.info("IFrame1.load()...");
        Wait<WebDriver> wait = new FluentWait<WebDriver>( driver )
                .withTimeout(30, TimeUnit.SECONDS)
                .pollingEvery(5, TimeUnit.SECONDS)
                .ignoring( NoSuchElementException.class ) 
                .ignoring( StaleElementReferenceException.class ) ;
            wait.until( ExpectedConditions.presenceOfElementLocated( 
            By.cssSelector("body form#webDriverUnitiFrame1TestFormID h1") ) );
    }
....

দ্রষ্টব্য: আপনি আমার পুরো কাজের উদাহরণটি এখানে দেখতে পারেন ।


1

জন্য nodejsসেলেনিয়াম গ্রন্থাগার, আমি নিম্নলিখিত স্নিপেট ব্যবহৃত। আমার ক্ষেত্রে, আমি উইন্ডোতে যুক্ত হওয়া দুটি বস্তুর সন্ধান করছিলাম, উদাহরণস্বরূপ <SOME PROPERTY>, 10000টাইমআউট মিলিসেকেন্ডগুলি, <NEXT STEP HERE>উইন্ডোটিতে বৈশিষ্ট্যগুলি সন্ধান করার পরে এটি ঘটে।

driver.wait( driver => {
    return driver.executeScript( 'if(window.hasOwnProperty(<SOME PROPERTY>) && window.hasOwnProperty(<SOME PROPERTY>)) return true;' ); }, 10000).then( ()=>{
        <NEXT STEP HERE>
}).catch(err => { 
    console.log("looking for window properties", err);
});

0

এটি পরিচালনা করতে আপনি কিছু যুক্তি লিখতে পারেন। আমি একটি পদ্ধতি লিখেছি যা প্রত্যাবর্তন করবে WebElementএবং এই পদ্ধতিটি তিনবার বলা হবে বা আপনি সময় বাড়িয়ে নাল চেক যুক্ত করতে পারেন WebElementএখানে একটি উদাহরণ

public static void main(String[] args) {
        WebDriver driver = new FirefoxDriver();
        driver.get("https://www.crowdanalytix.com/#home");
        WebElement webElement = getWebElement(driver, "homekkkkkkkkkkkk");
        int i = 1;
        while (webElement == null && i < 4) {
            webElement = getWebElement(driver, "homessssssssssss");
            System.out.println("calling");
            i++;
        }
        System.out.println(webElement.getTagName());
        System.out.println("End");
        driver.close();
    }

    public static WebElement getWebElement(WebDriver driver, String id) {
        WebElement myDynamicElement = null;
        try {
            myDynamicElement = (new WebDriverWait(driver, 10))
                    .until(ExpectedConditions.presenceOfElementLocated(By
                            .id(id)));
            return myDynamicElement;
        } catch (TimeoutException ex) {
            return null;
        }
    }

0

এখানে আমার নিজস্ব কোড থেকে:
উইন্ডো.সেটটাইমআউট তখনই কার্যকর করা হয় যখন ব্রাউজারটি নিষ্ক্রিয় থাকে।
সুতরাং ফাংশনটিকে পুনরাবৃত্তভাবে কল করতে (42 বার) ব্রাউজারটিতে কোনও ক্রিয়াকলাপ না থাকলে 100 মিমি এবং ব্রাউজারটি অন্য কিছু করতে ব্যস্ত থাকলে আরও অনেক কিছু গ্রহণ করবে।

    ExpectedCondition<Boolean> javascriptDone = new ExpectedCondition<Boolean>() {
        public Boolean apply(WebDriver d) {
            try{//window.setTimeout executes only when browser is idle,
                //introduces needed wait time when javascript is running in browser
                return  ((Boolean) ((JavascriptExecutor) d).executeAsyncScript( 

                        " var callback =arguments[arguments.length - 1]; " +
                        " var count=42; " +
                        " setTimeout( collect, 0);" +
                        " function collect() { " +
                            " if(count-->0) { "+
                                " setTimeout( collect, 0); " +
                            " } "+
                            " else {callback(" +
                            "    true" +                            
                            " );}"+                             
                        " } "
                    ));
            }catch (Exception e) {
                return Boolean.FALSE;
            }
        }
    };
    WebDriverWait w = new WebDriverWait(driver,timeOut);  
    w.until(javascriptDone);
    w=null;

কোনও বোনাস হিসাবে কাউন্টারটি ডকুমেন্ট.ডিয়ার স্টেটে বা jQuery অ্যাজাক্স কলগুলিতে বা কোনও jQuery অ্যানিমেশন চলমান থাকলে (কেবলমাত্র যদি আপনার অ্যাপ্লিকেশন এজ্যাক্স কলের জন্য jQuery ব্যবহার করে ...)
...

" function collect() { " +
                            " if(!((typeof jQuery === 'undefined') || ((jQuery.active === 0) && ($(\":animated\").length === 0))) && (document.readyState === 'complete')){" +
                            "    count=42;" +
                            "    setTimeout( collect, 0); " +
                            " }" +
                            " else if(count-->0) { "+
                                " setTimeout( collect, 0); " +
                            " } "+ 

...

সম্পাদনা: আমি লক্ষ্য করেছি এক্সিকিউট অ্যাক্সেস্ক্রিপ্ট ভাল কাজ করে না যদি কোনও নতুন পৃষ্ঠা লোড হয় এবং পরীক্ষাটি অনির্দিষ্টকালের জন্য প্রতিক্রিয়া বন্ধ করতে পারে, পরিবর্তে এটি ব্যবহার করা আরও ভাল।

public static ExpectedCondition<Boolean> documentNotActive(final int counter){ 
    return new ExpectedCondition<Boolean>() {
        boolean resetCount=true;
        @Override
        public Boolean apply(WebDriver d) {

            if(resetCount){
                ((JavascriptExecutor) d).executeScript(
                        "   window.mssCount="+counter+";\r\n" + 
                        "   window.mssJSDelay=function mssJSDelay(){\r\n" + 
                        "       if((typeof jQuery != 'undefined') && (jQuery.active !== 0 || $(\":animated\").length !== 0))\r\n" + 
                        "           window.mssCount="+counter+";\r\n" + 
                        "       window.mssCount-->0 &&\r\n" + 
                        "       setTimeout(window.mssJSDelay,window.mssCount+1);\r\n" + 
                        "   }\r\n" + 
                        "   window.mssJSDelay();");
                resetCount=false;
            }

            boolean ready=false;
            try{
                ready=-1==((Long) ((JavascriptExecutor) d).executeScript(
                        "if(typeof window.mssJSDelay!=\"function\"){\r\n" + 
                        "   window.mssCount="+counter+";\r\n" + 
                        "   window.mssJSDelay=function mssJSDelay(){\r\n" + 
                        "       if((typeof jQuery != 'undefined') && (jQuery.active !== 0 || $(\":animated\").length !== 0))\r\n" + 
                        "           window.mssCount="+counter+";\r\n" + 
                        "       window.mssCount-->0 &&\r\n" + 
                        "       setTimeout(window.mssJSDelay,window.mssCount+1);\r\n" + 
                        "   }\r\n" + 
                        "   window.mssJSDelay();\r\n" + 
                        "}\r\n" + 
                        "return window.mssCount;"));
            }
            catch (NoSuchWindowException a){
                a.printStackTrace();
                return true;
            }
            catch (Exception e) {
                e.printStackTrace();
                return false;
            }
            return ready;
        }
        @Override
        public String toString() {
            return String.format("Timeout waiting for documentNotActive script");
        }
    };
}

0

কীভাবে করবেন তা জানেন না তবে আমার ক্ষেত্রে, ফায়ারফক্স ট্যাবে প্রদর্শিত পৃষ্ঠার লোড ও রেন্ডারিংয়ের ম্যাচ শেষ হয়েছে VIC

সুতরাং আমরা যদি ওয়েব ব্রাউজারে ফেভিকন চিত্রটি পেতে পারি তবে ওয়েব পৃষ্ঠাটি সম্পূর্ণ লোড হয়ে গেছে।

তবে কিভাবে এটি সম্পাদন ....



-1

আমি এটি কীভাবে করব তা এখানে:

new WebDriverWait(driver, 20).until(
       ExpectedConditions.jsReturnsValue(
                   "return document.readyState === 'complete' ? true : false"));

সেলেনিয়াম এটি ডিফল্টরূপেও করে, এটি আপনার স্ক্রিপ্টে কিছু অতিরিক্ত কোড এক্সিকিউশন সময় যোগ করবে (অতিরিক্ত জিনিস লোড করার জন্য এটি যথেষ্ট সময় হতে পারে, তবে আবার তা নাও হতে পারে)
আর্দেসকো

-1

এটি স্থিতিশীল না হওয়া পর্যন্ত এইচটিএমএল পোলিংয়ের আপনার ধারণাটি আমি পছন্দ করি। আমি এটি আমার নিজের সমাধানে যুক্ত করতে পারি। নিম্নলিখিত পদ্ধতির সি # তে রয়েছে এবং jQuery প্রয়োজন।

আমি একটি সাফল্যফ্যাক্টর (সাস) পরীক্ষার প্রকল্পের বিকাশকারী যেখানে আমাদের বিকাশকারীদের উপর বা ওয়েব পৃষ্ঠার পিছনে ডিওএমের বৈশিষ্ট্যগুলির কোনও প্রভাব নেই। সাস পণ্যটি তার অন্তর্নিহিত ডিওএম নকশাটি বছরে 4 বার সম্ভাব্যভাবে পরিবর্তন করতে পারে, তাই স্লেইনিয়ামের সাথে পরীক্ষা করার জন্য শক্তিশালী, পারফরম্যান্স পদ্ধতিতে (স্থায়ীভাবে যেখানে সেলেনিয়ামের সাথে পরীক্ষা না করা সহ!

"পৃষ্ঠা প্রস্তুত" এর জন্য আমি যা ব্যবহার করি তা এখানে। এটি বর্তমানে আমার নিজের সমস্ত পরীক্ষায় কাজ করে। একই পদ্ধতি কয়েক বছর আগে একটি বড় ইন-হাউস জাভা ওয়েব অ্যাপ্লিকেশনটির জন্যও কাজ করেছিল এবং আমি প্রকল্পটি ছাড়ার সময় এক বছরেরও বেশি সময় ধরে দৃ .় ছিল।

  • Driver ওয়েবড্রাইভার উদাহরণ যা ব্রাউজারের সাথে যোগাযোগ করে
  • DefaultPageLoadTimeout টিক্সের একটি সময়সীমা মান (টিকিট প্রতি 100ns)

public IWebDriver Driver { get; private set; }

// ...

const int GlobalPageLoadTimeOutSecs = 10;
static readonly TimeSpan DefaultPageLoadTimeout =
    new TimeSpan((long) (10_000_000 * GlobalPageLoadTimeOutSecs));
Driver = new FirefoxDriver();

এরপরে, পদ্ধতিতে অপেক্ষা করার ক্রমটি নোট করুন PageReady(সেলেনিয়াম ডকুমেন্ট প্রস্তুত, অ্যাজাক্স, অ্যানিমেশন), আপনি যদি এটির বিষয়ে চিন্তা করেন তবে তা বোঝায়:

  1. কোডযুক্ত পৃষ্ঠাটি লোড করুন
  2. কোথাও থেকে অ্যাজাক্সের মাধ্যমে ডেটা লোড করতে কোডটি ব্যবহার করুন
  3. সম্ভবত অ্যানিমেশন সহ ডেটা উপস্থাপন করুন

দৃ D়তার অন্য স্তর যুক্ত করতে আপনার ডোম তুলনা পদ্ধতির মতো 1 থেকে 2 এর মধ্যে ব্যবহার করা যেতে পারে।


public void PageReady()
{
    DocumentReady();
    AjaxReady();
    AnimationsReady();
}


private void DocumentReady()
{
    WaitForJavascript(script: "return document.readyState", result: "complete");
}

private void WaitForJavascript(string script, string result)
{
    new WebDriverWait(Driver, DefaultPageLoadTimeout).Until(
        d => ((IJavaScriptExecutor) d).ExecuteScript(script).Equals(result));
}

private void AjaxReady()
{
    WaitForJavascript(script: "return jQuery.active.toString()", result: "0");
}

private void AnimationsReady()
{
    WaitForJavascript(script: "return $(\"animated\").length.toString()", result: "0");
}
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.