Ejemplo n.º 1
0
    def validatePage(self):
        start, end = self.get_start(), self.get_end()
        if isinstance(start, basestring) or isinstance(end, basestring):
            # do not check revisions
            return True
        try:
            start_date = to_datetime(start)
            end_date = to_datetime(end)
        except DateFormatError as exc:
            QMessageBox.critical(self, "Error", unicode(exc))
            return False
        current = datetime.datetime.now()
        if start_date < end_date:
            if end_date <= current:
                return True
            else:
                QMessageBox.critical(
                    self,
                    "Error",
                    "You can't define a date in the future.")
        else:
            QMessageBox.critical(
                self,
                "Error",
                "The first date must be earlier than the second one.")

        return False
Ejemplo n.º 2
0
    def validatePage(self):
        start, end = self.get_start(), self.get_end()
        if isinstance(start, basestring) or isinstance(end, basestring):
            # do not check revisions
            return True
        try:
            start_date = to_datetime(start)
            end_date = to_datetime(end)
        except DateFormatError as exc:
            QMessageBox.critical(self, "Error", unicode(exc))
            return False
        current = datetime.datetime.now()
        if start_date < end_date:
            if end_date <= current:
                return True
            else:
                QMessageBox.critical(
                    self,
                    "Error",
                    "You can't define a date in the future.")
        else:
            QMessageBox.critical(
                self,
                "Error",
                "The first date must be earlier than the second one.")

        return False
Ejemplo n.º 3
0
 def _print_progress(self, new_data):
     next_good_date = new_data[0].build_date
     next_bad_date = new_data[-1].build_date
     next_days_range = abs(
         (to_datetime(next_bad_date) - to_datetime(next_good_date)).days)
     LOG.info("Narrowed nightly regression window from"
              " [%s, %s] (%d days) to [%s, %s] (%d days)"
              " (~%d steps left)" %
              (self.good_date, self.bad_date,
               abs((to_datetime(self.bad_date) - to_datetime(
                   self.good_date)).days), next_good_date, next_bad_date,
               next_days_range, compute_steps_left(next_days_range)))
Ejemplo n.º 4
0
 def _print_progress(self, new_data):
     next_good_date = new_data[0].build_date
     next_bad_date = new_data[-1].build_date
     next_days_range = abs((to_datetime(next_bad_date) -
                            to_datetime(next_good_date)).days)
     LOG.info("Narrowed nightly regression window from"
              " [%s, %s] (%d days) to [%s, %s] (%d days)"
              " (~%d steps left)"
              % (self.good_date,
                 self.bad_date,
                 abs((to_datetime(self.bad_date) -
                      to_datetime(self.good_date)).days),
                 next_good_date,
                 next_bad_date,
                 next_days_range,
                 compute_steps_left(next_days_range)))
Ejemplo n.º 5
0
 def _check_date(obj):
     if is_date_or_datetime(obj):
         if to_datetime(obj) < time_limit:
             LOG.info("TaskCluster only keeps builds for one year."
                      " Using %s instead of %s." % (time_limit, obj))
             obj = time_limit
     return obj
Ejemplo n.º 6
0
    def find_inbound_changesets(self, days_required=4):
        self._logger.info("... attempting to bisect inbound builds (starting"
                          " from %d days prior, to make sure no inbound"
                          " revision is missed)" % days_required)
        infos = None
        days = days_required - 1
        too_many_attempts = False
        max_attempts = 3
        first_date = min(to_datetime(self.good_date),
                         to_datetime(self.bad_date))

        while not infos or not infos.changeset:
            days += 1
            if days >= days_required + max_attempts:
                too_many_attempts = True
                break
            prev_date = first_date - datetime.timedelta(days=days)
            build_range = self.build_range
            infos = build_range.build_info_fetcher.find_build_info(
                prev_date.date())
        if days > days_required and not too_many_attempts:
            self._logger.info("At least one build folder was invalid, we have"
                              " to start from %d days ago." % days)

        if not self.find_fix:
            good_rev = infos.changeset
            bad_rev = self.bad_revision
        else:
            good_rev = self.good_revision
            bad_rev = infos.changeset
        if bad_rev is None or good_rev is None:
            # we cannot find valid nightly builds in the searched range.
            # two possible causes:
            # - old nightly builds do not have the changeset information
            #   so we can't go on inbound. Anyway, these are probably too
            #   old and won't even exists on inbound.
            # - something else (builds were not updated on archive.mozilla.org,
            #   or all invalid)
            start_range = first_date - datetime.timedelta(days=days_required)
            end_range = start_range - datetime.timedelta(days=max_attempts)
            raise MozRegressionError(
                "Not enough changeset information to produce initial inbound"
                " regression range (failed to find metadata between %s and %s)"
                ". Nightly build folders are invalids or too old in this"
                " range." % (start_range, end_range))

        return good_rev, bad_rev
Ejemplo n.º 7
0
    def validatePage(self):
        try:
            start_date = to_datetime(self.get_start_date())
            end_date = to_datetime(self.get_end_date())
        except DateFormatError as exc:
            QMessageBox.critical(self, "Error", unicode(exc))
            return False
        current = datetime.datetime.now()
        if start_date < end_date:
            if end_date <= current:
                return True
            else:
                QMessageBox.critical(self, "Error", "You can't define a date in the future.")
        else:
            QMessageBox.critical(self, "Error", "The first date must be earlier than the second one.")

        return False
Ejemplo n.º 8
0
def check_nightlies(options, fetch_config, logger):
    default_bad_date = str(datetime.date.today())
    default_good_date = "2009-01-01"
    if mozinfo.os == 'win' and options.bits == 64:
        # first firefox build date for win64 is 2010-05-28
        default_good_date = "2010-05-28"
    if options.find_fix:
        default_bad_date, default_good_date = \
            default_good_date, default_bad_date
    # TODO: currently every fetch_config is nightly aware. Shoud we test
    # for this to be sure here ?
    fetch_config.set_nightly_repo(options.repo)
    if not options.bad_release and not options.bad_date:
        options.bad_date = default_bad_date
        logger.info("No 'bad' date specified, using %s" % options.bad_date)
    elif options.bad_release and options.bad_date:
        raise MozRegressionError("Options '--bad-release' and '--bad'"
                                 " are incompatible.")
    elif options.bad_release:
        options.bad_date = date_of_release(options.bad_release)
        logger.info("Using 'bad' date %s for release %s"
                    % (options.bad_date, options.bad_release))
    if not options.good_release and not options.good_date:
        options.good_date = default_good_date
        logger.info("No 'good' date specified, using %s"
                    % options.good_date)
    elif options.good_release and options.good_date:
        raise MozRegressionError("Options '--good-release' and '--good'"
                                 " are incompatible.")
    elif options.good_release:
        options.good_date = date_of_release(options.good_release)
        logger.info("Using 'good' date %s for release %s"
                    % (options.good_date, options.good_release))

    options.good_date = good_date = parse_date(options.good_date)
    options.bad_date = bad_date = parse_date(options.bad_date)
    if not options.find_fix and to_datetime(good_date) > to_datetime(bad_date):
        raise MozRegressionError(("Good date %s is later than bad date %s."
                                  " Maybe you wanted to use the --find-fix"
                                  " flag ?") % (good_date, bad_date))
    elif options.find_fix and to_datetime(good_date) < to_datetime(bad_date):
        raise MozRegressionError(("Bad date %s is later than good date %s."
                                  " You should not use the --find-fix flag"
                                  " in this case...") % (bad_date, good_date))
Ejemplo n.º 9
0
 def _check_date(obj):
     if is_date_or_datetime(obj):
         if to_datetime(obj) < time_limit:
             logger.info(
                 "TaskCluster only keeps builds for one year."
                 " Using %s instead of %s."
                 % (time_limit, obj)
             )
             obj = time_limit
     return obj
Ejemplo n.º 10
0
 def _print_progress(self, new_data):
     good_date, bad_date = self._reverse_if_find_fix(
         self.good_date, self.bad_date)
     next_good_date = new_data[0].build_date
     next_bad_date = new_data[-1].build_date
     next_days_range = abs(
         (to_datetime(next_bad_date) - to_datetime(next_good_date)).days)
     LOG.info("Narrowed nightly %s window from"
              " [%s, %s] (%d days) to [%s, %s] (%d days)"
              " (~%d steps left)" % (
                  "fix" if self.find_fix else "regression",
                  good_date,
                  bad_date,
                  abs((to_datetime(self.bad_date) -
                       to_datetime(self.good_date)).days),
                  next_good_date,
                  next_bad_date,
                  next_days_range,
                  compute_steps_left(next_days_range),
              ))
Ejemplo n.º 11
0
    def validate(self):
        """
        Validate the options, define the `action` and `fetch_config` that
        should be used to run the application.
        """
        options = self.options

        user_defined_bits = options.bits is not None
        options.bits = parse_bits(options.bits or mozinfo.bits)
        fetch_config = create_config(options.app, mozinfo.os, options.bits)
        try:
            fetch_config.set_build_type(options.build_type)
        except MozRegressionError as msg:
            self.logger.warning(
                "%s (Defaulting to %r)" % (msg, fetch_config.build_type)
            )
        self.fetch_config = fetch_config

        fetch_config.set_repo(options.repo)
        if fetch_config.is_nightly():
            fetch_config.set_base_url(options.archive_base_url)

        if not user_defined_bits and \
                options.bits == 64 and \
                mozinfo.os == 'win' and \
                32 in fetch_config.available_bits():
            # inform users on windows that we are using 64 bit builds.
            self.logger.info("bits option not specified, using 64-bit builds.")

        if options.bits == 32 and mozinfo.os == 'mac':
            self.logger.info("only 64-bit builds available for mac, using "
                             "64-bit builds")

        if fetch_config.is_inbound() and fetch_config.tk_needs_auth():
            creds = tc_authenticate(self.logger)
            fetch_config.set_tk_credentials(creds)

        # set action for just use changset or data to bisect
        if options.launch:
            options.launch = self._convert_to_bisect_arg(options.launch)
            self.action = "launch_inbound"
            if is_date_or_datetime(options.launch) and \
                    not fetch_config.should_use_taskcluster():
                self.action = "launch_nightlies"
        else:
            # define good/bad default values if required
            default_good_date, default_bad_date = \
                get_default_date_range(fetch_config)
            if options.find_fix:
                default_bad_date, default_good_date = \
                    default_good_date, default_bad_date
            if not options.bad:
                options.bad = default_bad_date
                self.logger.info("No 'bad' option specified, using %s"
                                 % options.bad)
            else:
                options.bad = self._convert_to_bisect_arg(options.bad)
            if not options.good:
                options.good = default_good_date
                self.logger.info("No 'good' option specified, using %s"
                                 % options.good)
            else:
                options.good = self._convert_to_bisect_arg(options.good)

            self.action = "bisect_inbounds"
            if is_date_or_datetime(options.good) and \
                    is_date_or_datetime(options.bad):
                if not options.find_fix and \
                        to_datetime(options.good) > to_datetime(options.bad):
                    raise MozRegressionError(
                        ("Good date %s is later than bad date %s."
                         " Maybe you wanted to use the --find-fix"
                         " flag?") % (options.good, options.bad))
                elif options.find_fix and \
                        to_datetime(options.good) < to_datetime(options.bad):
                    raise MozRegressionError(
                        ("Bad date %s is later than good date %s."
                         " You should not use the --find-fix flag"
                         " in this case...") % (options.bad, options.good))
                if not fetch_config.should_use_taskcluster():
                    self.action = "bisect_nightlies"
        if self.action in ('launch_inbound', 'bisect_inbounds')\
                and not fetch_config.is_inbound():
            raise MozRegressionError('Unable to bisect inbound for `%s`'
                                     % fetch_config.app_name)
        options.preferences = preferences(options.prefs_files, options.prefs)
        # convert GiB to bytes.
        options.persist_size_limit = \
            int(abs(float(options.persist_size_limit)) * 1073741824)
Ejemplo n.º 12
0
    def validate(self):
        """
        Validate the options, define the `action` and `fetch_config` that
        should be used to run the application.
        """
        options = self.options

        user_defined_bits = options.bits is not None
        options.bits = parse_bits(options.bits or mozinfo.bits)
        if options.arch is not None:
            if options.app != "gve":
                self.logger.warning("--arch ignored for non-GVE app.")
                options.arch = None

        fetch_config = create_config(options.app, mozinfo.os, options.bits,
                                     mozinfo.processor, options.arch)
        if options.lang:
            if options.app != "firefox-l10n":
                raise MozRegressionError(
                    "--lang is only valid with --app=firefox-l10n")
            fetch_config.set_lang(options.lang)
        elif options.app == "firefox-l10n":
            raise MozRegressionError(
                "app 'firefox-l10n' requires a --lang argument")
        if options.build_type:
            try:
                fetch_config.set_build_type(options.build_type)
            except MozRegressionError as msg:
                self.logger.warning("%s (Defaulting to %r)" %
                                    (msg, fetch_config.build_type))
        self.fetch_config = fetch_config

        fetch_config.set_repo(options.repo)
        fetch_config.set_base_url(options.archive_base_url)

        if (not user_defined_bits and options.bits == 64
                and mozinfo.os == "win"
                and 32 in fetch_config.available_bits()):
            # inform users on windows that we are using 64 bit builds.
            self.logger.info("bits option not specified, using 64-bit builds.")

        if options.bits == 32 and mozinfo.os == "mac":
            self.logger.info("only 64-bit builds available for mac, using "
                             "64-bit builds")

        if fetch_config.is_integration() and fetch_config.tk_needs_auth():
            creds = tc_authenticate(self.logger)
            fetch_config.set_tk_credentials(creds)

        # set action for just use changset or data to bisect
        if options.launch:
            options.launch = self._convert_to_bisect_arg(options.launch)
            self.action = "launch_integration"
            if is_date_or_datetime(
                    options.launch) and fetch_config.should_use_archive():
                self.action = "launch_nightlies"
        else:
            # define good/bad default values if required
            default_good_date, default_bad_date = get_default_date_range(
                fetch_config)
            if options.find_fix:
                default_bad_date, default_good_date = (
                    default_good_date,
                    default_bad_date,
                )
            if not options.bad:
                options.bad = default_bad_date
                self.logger.info("No 'bad' option specified, using %s" %
                                 options.bad)
            else:
                options.bad = self._convert_to_bisect_arg(options.bad)
            if not options.good:
                options.good = default_good_date
                self.logger.info("No 'good' option specified, using %s" %
                                 options.good)
            else:
                options.good = self._convert_to_bisect_arg(options.good)

            self.action = "bisect_integration"
            if is_date_or_datetime(options.good) and is_date_or_datetime(
                    options.bad):
                if not options.find_fix and to_datetime(
                        options.good) > to_datetime(options.bad):
                    raise MozRegressionError(
                        ("Good date %s is later than bad date %s."
                         " Maybe you wanted to use the --find-fix"
                         " flag?") % (options.good, options.bad))
                elif options.find_fix and to_datetime(
                        options.good) < to_datetime(options.bad):
                    raise MozRegressionError(
                        ("Bad date %s is later than good date %s."
                         " You should not use the --find-fix flag"
                         " in this case...") % (options.bad, options.good))
                if fetch_config.should_use_archive():
                    self.action = "bisect_nightlies"
        if (self.action in ("launch_integration", "bisect_integration")
                and not fetch_config.is_integration()):
            raise MozRegressionError("Unable to bisect integration for `%s`" %
                                     fetch_config.app_name)
        options.preferences = preferences(options.prefs_files, options.prefs,
                                          self.logger)
        # convert GiB to bytes.
        options.persist_size_limit = int(
            abs(float(options.persist_size_limit)) * 1073741824)
Ejemplo n.º 13
0
    def validate(self):
        """
        Validate the options, define the `action` and `fetch_config` that
        should be used to run the application.
        """
        options = self.options

        user_defined_bits = options.bits is not None
        options.bits = parse_bits(options.bits or mozinfo.bits)
        fetch_config = create_config(options.app, mozinfo.os, options.bits,
                                     mozinfo.processor)
        if options.build_type:
            try:
                fetch_config.set_build_type(options.build_type)
            except MozRegressionError as msg:
                self.logger.warning(
                    "%s (Defaulting to %r)" % (msg, fetch_config.build_type)
                )
        self.fetch_config = fetch_config

        fetch_config.set_repo(options.repo)
        if fetch_config.is_nightly():
            fetch_config.set_base_url(options.archive_base_url)

        if not user_defined_bits and \
                options.bits == 64 and \
                mozinfo.os == 'win' and \
                32 in fetch_config.available_bits():
            # inform users on windows that we are using 64 bit builds.
            self.logger.info("bits option not specified, using 64-bit builds.")

        if options.bits == 32 and mozinfo.os == 'mac':
            self.logger.info("only 64-bit builds available for mac, using "
                             "64-bit builds")

        if fetch_config.is_inbound() and fetch_config.tk_needs_auth():
            creds = tc_authenticate(self.logger)
            fetch_config.set_tk_credentials(creds)

        # set action for just use changset or data to bisect
        if options.launch:
            options.launch = self._convert_to_bisect_arg(options.launch)
            self.action = "launch_inbound"
            if is_date_or_datetime(options.launch) and \
                    not fetch_config.should_use_taskcluster():
                self.action = "launch_nightlies"
        else:
            # define good/bad default values if required
            default_good_date, default_bad_date = \
                get_default_date_range(fetch_config)
            if options.find_fix:
                default_bad_date, default_good_date = \
                    default_good_date, default_bad_date
            if not options.bad:
                options.bad = default_bad_date
                self.logger.info("No 'bad' option specified, using %s"
                                 % options.bad)
            else:
                options.bad = self._convert_to_bisect_arg(options.bad)
            if not options.good:
                options.good = default_good_date
                self.logger.info("No 'good' option specified, using %s"
                                 % options.good)
            else:
                options.good = self._convert_to_bisect_arg(options.good)

            self.action = "bisect_inbounds"
            if is_date_or_datetime(options.good) and \
                    is_date_or_datetime(options.bad):
                if not options.find_fix and \
                        to_datetime(options.good) > to_datetime(options.bad):
                    raise MozRegressionError(
                        ("Good date %s is later than bad date %s."
                         " Maybe you wanted to use the --find-fix"
                         " flag?") % (options.good, options.bad))
                elif options.find_fix and \
                        to_datetime(options.good) < to_datetime(options.bad):
                    raise MozRegressionError(
                        ("Bad date %s is later than good date %s."
                         " You should not use the --find-fix flag"
                         " in this case...") % (options.bad, options.good))
                if not fetch_config.should_use_taskcluster():
                    self.action = "bisect_nightlies"
        if self.action in ('launch_inbound', 'bisect_inbounds')\
                and not fetch_config.is_inbound():
            raise MozRegressionError('Unable to bisect inbound for `%s`'
                                     % fetch_config.app_name)
        options.preferences = preferences(options.prefs_files, options.prefs, self.logger)
        # convert GiB to bytes.
        options.persist_size_limit = \
            int(abs(float(options.persist_size_limit)) * 1073741824)