Script 'mail_helper' called by bg Hello packager, This is just FYI. Your package was checked in in distribution "sle12" by autobuild-member: bg. Here comes the log... ---------------------------%<------------------------------ Hi, here is the log from ci_new_pac /mounts/work_src_done/SLE12/yast2-registration -> sle12 ## BNC# 880685 : "Hint where to find the license is wrong" (RESOLVED/FIXED) ## BNC# 880941 : "[UPGRADE] Asked for registration server even if registration was skipped" (RESOLVED/FIXED) ## BNC# 873185 : "GEO Extension (to HA extension) does not show-up in the list of extensions during installation" (RESOLVED/FIXED) Changes: -------- --- /work/SRC/SUSE:SLE-12:GA/yast2-registration/yast2-registration.changes 2014-06-06 17:22:34.000000000 +0200 +++ /mounts/work_src_done/SLE12/yast2-registration/yast2-registration.changes 2014-06-09 13:57:42.000000000 +0200 @@ -1,0 +2,27 @@ +Mon Jun 9 11:26:18 UTC 2014 - lslezak@suse.cz + +- display where to download the extension EULA text (bnc#880685) +- 3.1.69 + +------------------------------------------------------------------- +Mon Jun 9 08:02:03 UTC 2014 - jreidinger@suse.com + +- switch build tool from autotools to yast-rake +- 3.1.68 + +------------------------------------------------------------------- +Fri Jun 6 15:27:28 UTC 2014 - lslezak@suse.cz + +- properly leave the addon workflow when registration was skipped + (bnc#880941) +- 3.1.67 + +------------------------------------------------------------------- +Fri Jun 6 11:41:21 UTC 2014 - jreidinger@suse.com + +- added support for nested extensions to display e.g. HA GEO + extension (bnc#873185) +- improve test coverage +- 3.1.66 + +------------------------------------------------------------------- calling whatdependson for sle12-i586 Packages directly triggered for rebuild: - yast2-registration ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/SUSE:SLE-12:GA/yast2-registration (Old) and /mounts/work_src_done/SLE12/yast2-registration (BS:build ID:39165 MAIL:yast-commit@opensuse.org) (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Package is "yast2-registration", Maintainer is "yast-commit@opensuse.org" Old: ---- yast2-registration-3.1.65.tar.bz2 New: ---- yast2-registration-3.1.69.tar.bz2 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ yast2-registration.spec ++++++ --- /var/tmp/diff_new_pack.j60Fmc/_old 2014-06-10 15:14:12.000000000 +0200 +++ /var/tmp/diff_new_pack.j60Fmc/_new 2014-06-10 15:14:12.000000000 +0200 @@ -17,7 +17,7 @@ Name: yast2-registration -Version: 3.1.65 +Version: 3.1.69 Release: 0 BuildRoot: %{_tmppath}/%{name}-%{version}-build @@ -31,18 +31,19 @@ Requires: yast2-pkg-bindings >= 2.17.20 # N_() method Requires: yast2-ruby-bindings >= 3.1.12 -Requires: rubygem-suse-connect >= 0.0.18 +Requires: rubygem-suse-connect >= 0.0.19 Requires: yast2-slp >= 3.1.2 Requires: yast2-add-on >= 3.1.8 -Requires: yast2-packager >= 3.1.21 +Requires: yast2-packager >= 3.1.22 BuildRequires: yast2 >= 3.1.26 BuildRequires: update-desktop-files BuildRequires: yast2-devtools >= 3.1.6 +BuildRequires: rubygem-yast-rake >= 0.1.8 BuildRequires: rubygem-rspec -BuildRequires: rubygem-suse-connect >= 0.0.18 +BuildRequires: rubygem-suse-connect >= 0.0.19 BuildRequires: yast2-slp >= 3.1.2 -BuildRequires: yast2-packager >= 3.1.21 +BuildRequires: yast2-packager >= 3.1.22 BuildArch: noarch @@ -62,10 +63,13 @@ %setup -n %{name}-%{version} %build -%yast_build + +%check +rake test:unit %install -%yast_install +rake install DESTDIR="%{buildroot}" +%suse_update_desktop_file customer_center %files ++++++ yast2-registration-3.1.65.tar.bz2 -> yast2-registration-3.1.69.tar.bz2 ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/configure.ac.in new/yast2-registration-3.1.69/configure.ac.in --- old/yast2-registration-3.1.65/configure.ac.in 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/configure.ac.in 1970-01-01 01:00:00.000000000 +0100 @@ -1,12 +0,0 @@ -## YCP module configure.in.in - -## Initialize -@YAST2-INIT-COMMON@ -@YAST2-INIT-YCP@ - -## some common checks -@YAST2-CHECKS-COMMON@ -@YAST2-CHECKS-YCP@ - -## and generate the output... -@YAST2-OUTPUT@ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/Makefile.cvs new/yast2-registration-3.1.69/Makefile.cvs --- old/yast2-registration-3.1.65/Makefile.cvs 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/Makefile.cvs 1970-01-01 01:00:00.000000000 +0100 @@ -1,23 +0,0 @@ -# -# Makefile.cvs -# - -LIB = $(shell y2tool get-lib) - -PREFIX = /usr - -configure: all - ./configure --prefix=$(PREFIX) --libdir=$(PREFIX)/$(LIB) - -all: - y2tool y2autoconf - y2tool y2automake - autoreconf --force --install - -install: configure - make - make install - -reconf: all - ./config.status --recheck - ./config.status diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/package/yast2-registration.changes new/yast2-registration-3.1.69/package/yast2-registration.changes --- old/yast2-registration-3.1.65/package/yast2-registration.changes 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/package/yast2-registration.changes 2014-06-10 11:13:02.000000000 +0200 @@ -1,4 +1,31 @@ ------------------------------------------------------------------- +Mon Jun 9 11:26:18 UTC 2014 - lslezak@suse.cz + +- display where to download the extension EULA text (bnc#880685) +- 3.1.69 + +------------------------------------------------------------------- +Mon Jun 9 08:02:03 UTC 2014 - jreidinger@suse.com + +- switch build tool from autotools to yast-rake +- 3.1.68 + +------------------------------------------------------------------- +Fri Jun 6 15:27:28 UTC 2014 - lslezak@suse.cz + +- properly leave the addon workflow when registration was skipped + (bnc#880941) +- 3.1.67 + +------------------------------------------------------------------- +Fri Jun 6 11:41:21 UTC 2014 - jreidinger@suse.com + +- added support for nested extensions to display e.g. HA GEO + extension (bnc#873185) +- improve test coverage +- 3.1.66 + +------------------------------------------------------------------- Thu Jun 5 12:43:27 UTC 2014 - jsrain@suse.cz - add explanation to extension regcode dialog (bnc#881466) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/package/yast2-registration.spec new/yast2-registration-3.1.69/package/yast2-registration.spec --- old/yast2-registration-3.1.65/package/yast2-registration.spec 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/package/yast2-registration.spec 2014-06-10 11:13:03.000000000 +0200 @@ -17,7 +17,7 @@ Name: yast2-registration -Version: 3.1.65 +Version: 3.1.69 Release: 0 BuildRoot: %{_tmppath}/%{name}-%{version}-build @@ -31,18 +31,19 @@ Requires: yast2-pkg-bindings >= 2.17.20 # N_() method Requires: yast2-ruby-bindings >= 3.1.12 -Requires: rubygem-suse-connect >= 0.0.18 +Requires: rubygem-suse-connect >= 0.0.19 Requires: yast2-slp >= 3.1.2 Requires: yast2-add-on >= 3.1.8 -Requires: yast2-packager >= 3.1.21 +Requires: yast2-packager >= 3.1.22 BuildRequires: yast2 >= 3.1.26 BuildRequires: update-desktop-files BuildRequires: yast2-devtools >= 3.1.6 +BuildRequires: rubygem-yast-rake >= 0.1.8 BuildRequires: rubygem-rspec -BuildRequires: rubygem-suse-connect >= 0.0.18 +BuildRequires: rubygem-suse-connect >= 0.0.19 BuildRequires: yast2-slp >= 3.1.2 -BuildRequires: yast2-packager >= 3.1.21 +BuildRequires: yast2-packager >= 3.1.22 BuildArch: noarch @@ -62,10 +63,13 @@ %setup -n %{name}-%{version} %build -%yast_build + +%check +rake test:unit %install -%yast_install +rake install DESTDIR="%{buildroot}" +%suse_update_desktop_file customer_center %files diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/src/clients/inst_scc.rb new/yast2-registration-3.1.69/src/clients/inst_scc.rb --- old/yast2-registration-3.1.65/src/clients/inst_scc.rb 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/src/clients/inst_scc.rb 2014-06-10 11:13:03.000000000 +0200 @@ -27,6 +27,7 @@ require "cgi" +require "registration/addon" require "registration/exceptions" require "registration/helpers" require "registration/connect_helpers" @@ -34,6 +35,7 @@ require "registration/storage" require "registration/registration" require "registration/ui/addon_eula_dialog" +require "registration/ui/addon_selection_dialog" module Yast class InstSccClient < Client @@ -94,6 +96,7 @@ show_scc_credentials_dialog ret = nil + @registration_skipped = false continue_buttons = [:next, :back, :cancel, :abort] while !continue_buttons.include?(ret) do @@ -159,7 +162,10 @@ end end - return ret if ret == :skip && confirm_skipping + if ret == :skip && confirm_skipping + @registration_skipped = true + return ret + end end return ret @@ -307,164 +313,15 @@ ::Registration::SwMgmt.set_repos_state(updates, options.install_updates) end - # create item list (available addons items) - def addon_selection_items(addons) - box = VBox() - - # whether to add extra spacing in the UI - if UI.TextMode - add_extra_spacing = addons.size < 5 - else - add_extra_spacing = true - end - - addons.each do |addon| - label = addon.short_name - label << " (#{addon.long_name})" if addon.long_name && !addon.long_name.empty? - - box.params << Left(CheckBox(Id(addon.product_ident), - Opt(:notify), - addon.short_name, - @selected_addons.include?(addon) || registered_addons.include?(addon.product_ident))) - - # add extra spacing when there are just few addons, in GUI always - box.params << VSpacing(0.7) if add_extra_spacing - end - - box - end - - # create content fot the addon selection dialog - def addon_selection_dialog_content(addons) - # less lines in textmode to fit 80x25 size - lines = UI.TextMode ? 9 : 14 - - # use two column layout if needed - vbox1 = addon_selection_items(addons[0..(lines - 1)]) - vbox2 = (addons.size > lines) ? HBox( - HSpacing(1), - VBox( - addon_selection_items(addons[lines..(2*lines - 1)]), - VStretch() - ) - ) : - Empty() - - VBox( - VStretch(), - Left(Heading(_("Available Extensions and Modules"))), - VWeight(75, MarginBox(2, 1, HBox( - vbox1, - vbox2 - ))), - Left(Label(_("Details"))), - MinHeight(8, - VWeight(25, RichText(Id(:details), Opt(:disabled), "<small>" + - _("Select an extension or a module to show details here") + "</small>")), - ), - VStretch() - ) - end - - # update addon details after changing the current addon in the UI - def show_addon_details(addon) - # addon description is a rich text - UI.ChangeWidget(Id(:details), :Value, addon.description) - UI.ChangeWidget(Id(:details), :Enabled, true) - end - - # check addon dependencies and automatically select required addons - def check_addon_dependencies(addons) - selected = UI.QueryWidget(Id(:addons), :SelectedItems) - selected_addons = addons.select{|a| selected.include?(a.name)} - - selected_addons.each do |a| - missing = a.required_addons - selected_addons - - if !missing.empty? - # popup message, %s are product names - Popup.Message((_("Automatically selecting '%s'\ndependencies:\n\n%s") % - [a.label, missing.map(&:label).join("\n")])) - # select the missing entries - UI.ChangeWidget(Id(:addons), :SelectedItems, selected + missing.map(&:name)) - end - end - end - - # check for the maximum amount of reg. codes supported by Yast - def supported_addon_count(selected) - # maximum number or reg codes which can be displayed in two column layout - max_supported = 2*MAX_REGCODES_PER_COLUMN - - # check the addons requiring a reg. code - if selected.count{|a| !a.free} > max_supported - Report.Error(_("YaST allows to select at most %s addons.") % max_supported) - return false - end - - return true - end - - # handle user input in the addon selection dialog - def handle_addon_selection_dialog(addons) - ret = nil - continue_buttons = [:next, :back, :close, :abort, :skip] - - while !continue_buttons.include?(ret) do - ret = UI.UserInput - - case ret - when :next - selected = addons.select{|a| UI.QueryWidget(Id(a.product_ident), :Value)} - - # ignore already registered addons - selected.reject!{|a| registered_addons.include?(a.product_ident) } - - if !supported_addon_count(selected) - ret = nil - next - end - - @selected_addons = selected - ::Registration::Storage::InstallationOptions.instance.selected_addons = @selected_addons - log.info "Selected addons: #{@selected_addons.map(&:short_name)}" - - ret = :skip if @selected_addons.empty? - else - # check whether it's an add-on ID (checkbox clicked) - addon = addons.find{|addon| addon.product_ident == ret} - - # an addon has been changed, refresh details, check dependencies - if addon - show_addon_details(addon) - # TODO FIXME: SCC does not support dependencies yet - # check_addon_dependencies(addons) - end - end - end - - ret - end - # run the addon selection dialog def select_addons - addons = get_available_addons - Wizard.SetContents( - # dialog title - _("Extension Selection"), - addon_selection_dialog_content(addons), - # TODO FIXME: add a help text - "", - GetInstArgs.enable_back || Mode.normal, - GetInstArgs.enable_next || Mode.normal - ) + get_available_addons # FIXME just to fill cache with popup - # disable already registered addons in UI - registered_addons.each do |addon| - UI.ChangeWidget(Id(addon), :Enabled, false) - end + # FIXME workaround to reference between old way and new storage in Addon metaclass + @selected_addons = Registration::Addon.selected + ::Registration::Storage::InstallationOptions.instance.selected_addons = @selected_addons - handle_addon_selection_dialog(addons) + Registration::UI::AddonSelectionDialog.run(@registration) end @@ -535,19 +392,15 @@ # installation workflow def get_available_addons # cache the available addons - @available_addons = ::Registration::Storage::Cache.instance.available_addons - return @available_addons if @available_addons - init_registration @available_addons = Popup.Feedback( _(CONTACTING_MESSAGE), _("Loading Available Add-on Products and Extensions...")) do - @registration.get_addon_list + Registration::Addon.find_all(@registration) end - log.info "Received product extensions: #{@available_addons}" ::Registration::Storage::Cache.instance.available_addons = @available_addons @available_addons end @@ -685,6 +538,9 @@ ) ret = :next if [:auto, :finish].include?(ret) + # leave the workflow if registration was skipped + ret = :finish if ret == :next && @registration_skipped + return ret end @@ -756,7 +612,7 @@ return :register end end - + def addon_eula ::Registration::UI::AddonEulaDialog.run(@selected_addons) end @@ -805,6 +661,7 @@ "media_addons" => { :abort => :abort, :next => "addon_eula", + :finish => :next }, "addon_eula" => { :abort => :abort, @@ -829,7 +686,7 @@ # helper method for accessing the registered addons def registered_addons - ::Registration::Storage::Cache.instance.registered_addons + Registration::Addon.registered end end unless defined?(InstSccClient) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/src/lib/registration/addon.rb new/yast2-registration-3.1.69/src/lib/registration/addon.rb --- old/yast2-registration-3.1.65/src/lib/registration/addon.rb 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/src/lib/registration/addon.rb 2014-06-10 11:13:03.000000000 +0200 @@ -19,66 +19,69 @@ # ------------------------------------------------------------------------------ # -require 'tsort' +require "forwardable" module Registration class Addon - # product data needed for registration - attr_reader :name, :version, :arch - # additional data: UI labels, dependencies on other add-ons and - # a flag indicating required registration code - attr_reader :label, :description, :depends_on, :regcode_needed - - def initialize(name, version, arch, label: "", description: "", - depends_on: [], regcode_needed: true) - @name = name - @version = version - @arch = arch - @label = label - @description = description - @depends_on = depends_on - @regcode_needed = regcode_needed - end - - # recursively collect all addon dependecies and create a flat list - # @return [Array<Addon>] - def required_addons - # this addon dependencies plus their dependencies - depends_on.inject(depends_on.dup) do |acc, dep| - acc.concat(dep.required_addons) - # remove duplicates - acc.uniq + class << self + def find_all(registration) + return @cached_addons if @cached_addons + pure_addons = registration.get_addon_list + @cached_addons = pure_addons.reduce([]) do |res, addon| + res.concat(create_addon_with_deps(addon)) + end end - end - end - # class for sorting Addons according to their dependencies - # SCC requires to register addons in their dependency order - # @see TSort example http://ruby-doc.org/stdlib-2.1.0/libdoc/tsort/rdoc/TSort.html#module-TSort-l... - class AddonSorter < Hash - include TSort - - alias tsort_each_node each_key - - def tsort_each_child(node, &block) - fetch(node).each(&block) - end - - # computes registration order of add-ons acording to their dependencies - # raises KeyError on missing dependency - # @param addons [Array<Addons>] input list with addons - # @return [Array<Addons>] input list sorted according to Addon dependencies - def self.registration_order(addons) - solver = AddonSorter.new - - # fill the solver with addon dependencies - addons.each do |a| - solver[a] = a.depends_on + def registered + @registered ||= [] end - # compute the order using tsort - solver.tsort + def selected + @selected ||= [] + end + + private + + def create_addon_with_deps(root) + root_addon = Addon.new(root) + result = [ root_addon ] + + (root.extensions || []).each do |ext| + child = create_addon_with_deps(ext) + result.concat(child) + child.first.depends_on = root_addon + root_addon.children << child.first + end + + return result + end end - end + extend Forwardable + + attr_reader :children + attr_accessor :depends_on, :regcode + + def_delegators :@pure_addon, :free, :product_ident, :short_name, :long_name, :description, :eula_url + def initialize pure_addon + @pure_addon = pure_addon + @children = [] + end + + def selected? + Addon.selected.include?(self) + end + + def selected + Addon.selected << self unless selected? + end + + def unselected + Addon.selected.delete(self) if selected? + end + + def registered? + Addon.registered.include?(self) + end + end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/src/lib/registration/ui/addon_eula_dialog.rb new/yast2-registration-3.1.69/src/lib/registration/ui/addon_eula_dialog.rb --- old/yast2-registration-3.1.65/src/lib/registration/ui/addon_eula_dialog.rb 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/src/lib/registration/ui/addon_eula_dialog.rb 2014-06-10 11:13:03.000000000 +0200 @@ -86,7 +86,7 @@ id = "#{addon.short_name} extension EULA" Yast::ProductLicense.SetAcceptanceNeeded(id, true) - # TODO reset ProductLicense::license_file_print attribute + Yast::ProductLicense.license_file_print = addon.eula_url # %s is an extension name, e.g. "SUSE Linux Enterprise Software Development Kit" title = _("%s License Agreement") % addon.short_name diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/src/lib/registration/ui/addon_selection_dialog.rb new/yast2-registration-3.1.69/src/lib/registration/ui/addon_selection_dialog.rb --- old/yast2-registration-3.1.65/src/lib/registration/ui/addon_selection_dialog.rb 1970-01-01 01:00:00.000000000 +0100 +++ new/yast2-registration-3.1.69/src/lib/registration/ui/addon_selection_dialog.rb 2014-06-10 11:13:03.000000000 +0200 @@ -0,0 +1,218 @@ + +require "yast" +require "registration/addon" +require "registration/helpers" + +module Registration + module UI + + class AddonSelectionDialog + include Yast::Logger + include Yast::I18n + include Yast::UIShortcuts + include Yast + + Yast.import "Mode" + Yast.import "GetInstArgs" + Yast.import "Popup" + Yast.import "Report" + Yast.import "UI" + Yast.import "Wizard" + + # create a new dialog for accepting importing a SSL certificate and run it + def self.run(registration) + dialog = AddonSelectionDialog.new(registration) + dialog.run + end + + def initialize(registration) + textdomain "registration" + @addons = Addon.find_all(registration) + end + + # display the EULA for each dialog and wait for a button click + # @return [Symbol] user input (:import, :cancel) + def run + Wizard.SetContents( + # dialog title + _("Extension Selection"), + content, + # TODO FIXME: add a help text + "", + GetInstArgs.enable_back || Mode.normal, #FIXME make parameters + GetInstArgs.enable_next || Mode.normal + ) + + @old_selection = Addon.selected.dup + + reactivate_dependencies + + handle_dialog + end + + private + + def content + VBox( + VStretch(), + Left(Heading(_("Available Extensions and Modules"))), + addons_box, + Left(Label(_("Details"))), + MinHeight(8, + VWeight(25, RichText(Id(:details), Opt(:disabled), "<small>" + + _("Select an extension or a module to show details here") + "</small>")), + ), + VStretch() + ) + end + + def addons_box + lines = Yast::UI.TextMode ? 9 : 14 + if @addons.size <= lines + content = addon_selection_items(@addons) + else + box2 = addon_selection_items(@addons[lines..(2*lines - 1)]) + box2.params << VStretch() # just UI tweak + content = HBox( + addon_selection_items(@addons[0..(lines - 1)]), + HSpacing(1), + box2 + ) + end + + VWeight(75, MarginBox(2, 1, content)) + end + + def addon_selection_items(addons) + box = VBox() + + # whether to add extra spacing in the UI + if Yast::UI.TextMode + add_extra_spacing = addons.size < 5 + else + add_extra_spacing = true + end + + addons.each do |addon| + box.params.concat(addon_checkbox(addon, add_extra_spacing)) + end + + box + end + + # @return [Array] Return array with one or two elements for VBox + def addon_checkbox(addon, extra_spacing) + checkbox = Left(addon_checkbox_element(addon)) + + # usability help. If addon depends on something, then we get it + # immediatelly after parent, so indent it slightly, so it is easier visible + if addon.depends_on + checkbox = HBox(HSpacing(2.5), checkbox) + end + res = [checkbox] + # add extra spacing when there are just few addons, in GUI always + res << VSpacing(0.7) if extra_spacing + + return res + end + + def addon_checkbox_element(addon) + CheckBox(Id(addon.product_ident), + Opt(:notify), + addon.short_name, + addon.selected? || addon.registered?) + end + + def handle_dialog + ret = nil + continue_buttons = [:next, :back, :close, :abort, :skip] + + while !continue_buttons.include?(ret) do + ret = Yast::UI.UserInput + + case ret + when :next + ret = handle_next_button + # when canceled switch to old selection + when :close, :abort + Addon.selected.replace(@old_selection) + else + handle_addon_selection(ret) + end + end + + ret + end + + def handle_next_button + if !supported_addon_count? + return nil + end + + log.info "Selected addons: #{Addon.selected.map(&:short_name)}" + + Addon.selected.empty? ? :skip : :next + end + + def handle_addon_selection(id) + # check whether it's an add-on ID (checkbox clicked) + addon = @addons.find{|addon| addon.product_ident == id} + return unless addon + + show_addon_details(addon) + if Yast::UI.QueryWidget(Id(addon.product_ident), :Value) + addon.selected + else + addon.unselected + end + reactivate_dependencies + end + + + # update addon details after changing the current addon in the UI + def show_addon_details(addon) + # addon description is a rich text + Yast::UI.ChangeWidget(Id(:details), :Value, addon.description) + Yast::UI.ChangeWidget(Id(:details), :Enabled, true) + end + + + def reactivate_dependencies + @addons.each do |addon| + Yast::UI.ChangeWidget(Id(addon.product_ident), :Enabled, enable_addon?(addon)) + end + end + + def enable_addon?(addon) + # Do not support unregister + return false if addon.registered? + # Do not allow to select child without selected parent + return false if addon.depends_on && !addon.depends_on.selected? + # Do not allow to unselect parent if any children is selected + return false if addon.children.any?(&:selected?) + + return true + end + + # the maximum number of reg. codes displayed vertically, + # this is the limit for 80x25 textmode UI + MAX_REGCODES_PER_COLUMN = 8 + + # check for the maximum amount of reg. codes supported by Yast + def supported_addon_count? + need_regcode = Addon.selected.reject(&:registered?).reject(&:free) + # maximum number or reg codes which can be displayed in two column layout + max_supported = 2*MAX_REGCODES_PER_COLUMN + + # check the addons requiring a reg. code + if need_regcode.size > max_supported + Report.Error(_("YaST allows to select at most %s addons.") % max_supported) + return false + end + + return true + end + end + end +end + diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/src/Makefile.am new/yast2-registration-3.1.69/src/Makefile.am --- old/yast2-registration-3.1.65/src/Makefile.am 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/src/Makefile.am 1970-01-01 01:00:00.000000000 +0100 @@ -1,44 +0,0 @@ -# Sources for installation - -client_DATA = \ - clients/discover_registration_services.rb \ - clients/inst_scc.rb \ - clients/scc.rb \ - clients/scc_auto.rb - -desktop_DATA = \ - desktop/customer_center.desktop - -ylibdir = @ylibdir@/registration -ylib_DATA = \ - lib/registration/addon.rb \ - lib/registration/exceptions.rb \ - lib/registration/eula_downloader.rb \ - lib/registration/sw_mgmt.rb \ - lib/registration/storage.rb \ - lib/registration/registration.rb \ - lib/registration/helpers.rb \ - lib/registration/connect_helpers.rb - -ylibuidir = @ylibdir@/registration/ui -ylibui_DATA = \ - lib/registration/ui/addon_eula_dialog.rb \ - lib/registration/ui/import_certificate_dialog.rb - -ylibyastdir = @ylibdir@/yast -ylibyast_DATA = \ - lib/yast/suse_connect.rb - -schemafilesdir = $(schemadir)/autoyast/rnc -schemafiles_DATA = \ - autoyast-rnc/registration.rnc - -ydatadir = @ydatadir@/registration -ydata_DATA = \ - data/registration/certificate_summary.erb \ - data/registration/autoyast_summary.erb - -EXTRA_DIST = $(client_DATA) $(desktop_DATA) $(ylib_DATA) $(ylibui_DATA) \ - $(ylibyast_DATA) $(schemafiles_DATA) $(ydata_DATA) - -include $(top_srcdir)/Makefile.am.common diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/test/addon_selection_dialog_test.rb new/yast2-registration-3.1.69/test/addon_selection_dialog_test.rb --- old/yast2-registration-3.1.65/test/addon_selection_dialog_test.rb 1970-01-01 01:00:00.000000000 +0100 +++ new/yast2-registration-3.1.69/test/addon_selection_dialog_test.rb 2014-06-10 11:13:03.000000000 +0200 @@ -0,0 +1,44 @@ +require_relative "spec_helper" +require "registration/ui/addon_selection_dialog" + +describe Registration::UI::AddonSelectionDialog do + subject { Registration::UI::AddonSelectionDialog } + + before(:each) do + # generic UI stubs for the wizard dialog + stub_const("Yast::UI", double()) + allow(Yast::UI).to receive(:WizardCommand) + allow(Yast::UI).to receive(:WidgetExists).and_return(true) + allow(Yast::UI).to receive(:ChangeWidget) + allow(Yast::UI).to receive(:SetFocus) + allow(Yast::UI).to receive(:ReplaceWidget) + allow(Yast::UI).to receive(:TextMode).and_return(false) + + addon_reset_cache + end + + describe ".run" do + it "returns response from addon selection according to pressed button" do + expect(Yast::UI).to receive(:UserInput).and_return(:abort) + registration = double(:get_addon_list => []) + expect(subject.run(registration)).to eq :abort + end + + it "returns `:skip` if no addon is selected and user click next" do + expect(Yast::UI).to receive(:UserInput).and_return(:next) + registration = double(:get_addon_list => []) + expect(subject.run(registration)).to eq :skip + end + + it "returns `:next` if some addons are selected and user click next" do + test_addon = addon_generator + expect(Yast::UI).to receive(:UserInput).and_return(test_addon.product_ident, :next) + # mock that widget is selected + expect(Yast::UI).to receive(:QueryWidget). + with(Yast::Term.new(:id, test_addon.product_ident), :Value). + and_return(true) + registration = double(:get_addon_list => [test_addon]) + expect(subject.run(registration)).to eq :next + end + end +end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/test/addon_spec.rb new/yast2-registration-3.1.69/test/addon_spec.rb --- old/yast2-registration-3.1.65/test/addon_spec.rb 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/test/addon_spec.rb 2014-06-10 11:13:03.000000000 +0200 @@ -3,91 +3,95 @@ require_relative "spec_helper" require "registration/addon" +require "suse/connect" describe Registration::Addon do - describe ".required_addons" do - it "returns empty list if there are no dependencies" do - addon = Registration::Addon.new("SUSE_SLES", "12", "x86_64") + before(:each) do + addon_reset_cache + end + + subject(:addon) do + Registration::Addon.new(addon_generator) + end + + describe ".find_all" do + it "find all addons for current base product" do + prod1 = addon_generator + prod2 = addon_generator + registration = double(:get_addon_list => [prod1, prod2]) - expect(addon.required_addons).to be_empty + expect(Registration::Addon.find_all(registration).size).to be 2 end - it "returns an array containing the dependency name" do - addon1 = Registration::Addon.new("SUSE_ADDON1", "12", "x86_64") - addon2 = Registration::Addon.new("SUSE_ADDON2", "12", "x86_64", depends_on: [addon1]) + it "find even dependend products" do + prod1 = addon_with_child_generator + registration = double(:get_addon_list => [prod1]) - expect(addon2.required_addons).to eq([addon1]) + expect(Registration::Addon.find_all(registration).size).to be 2 end - it "removes duplicates" do - addon1 = Registration::Addon.new("SUSE_ADDON1", "12", "x86_64") - addon2 = Registration::Addon.new("SUSE_ADDON2", "12", "x86_64", depends_on: [addon1]) - addon3 = Registration::Addon.new("SUSE_ADDON3", "12", "x86_64", depends_on: [addon1]) - addon4 = Registration::Addon.new("SUSE_ADDON3", "12", "x86_64", depends_on: [addon1]) - addon5 = Registration::Addon.new("SUSE_ADDON3", "12", "x86_64", depends_on: [addon2, addon3, addon4]) + it "sets properly dependencies between addons" do + prod1 = addon_with_child_generator + registration = double(:get_addon_list => [prod1]) - required_addons = addon5.required_addons + addons = Registration::Addon.find_all(registration) + expect(addons.any? {|addon| addon.children.size == 1}).to be_true + expect(addons.any?(&:depends_on)).to be_true + end + end - expect(required_addons).to eq(required_addons.uniq) - expect(required_addons).to include(addon1, addon2, addon3, addon4) + describe ".selected" do + it "returns array with selected addons" do + expect(Registration::Addon.selected).to be_a(Array) end + end - it "returns transitive dependencies" do - addon1 = Registration::Addon.new("SUSE_ADDON1", "12", "x86_64") - addon2 = Registration::Addon.new("SUSE_ADDON2", "12", "x86_64", depends_on: [addon1]) - addon3 = Registration::Addon.new("SUSE_ADDON3", "12", "x86_64", depends_on: [addon2]) + describe ".registered" do + it "returns array of already registered addons" do + expect(Registration::Addon.registered).to be_a(Array) + end + end - expect(addon3.required_addons).to include(addon1, addon2) + describe "#selected?" do + it "returns if addon is selected for installation" do + expect(addon.selected?).to be_false + Registration::Addon.selected << addon + expect(addon.selected?).to be_true end + end - it "returns multiple transitive dependencies" do - addon1 = Registration::Addon.new("SUSE_ADDON1", "12", "x86_64") - addon2 = Registration::Addon.new("SUSE_ADDON2", "12", "x86_64") - addon3 = Registration::Addon.new("SUSE_ADDON3", "12", "x86_64", depends_on: [addon1, addon2]) - addon4 = Registration::Addon.new("SUSE_ADDON4", "12", "x86_64") - addon5 = Registration::Addon.new("SUSE_ADDON5", "12", "x86_64") - addon6 = Registration::Addon.new("SUSE_ADDON6", "12", "x86_64", depends_on: [addon4, addon5]) - addon7 = Registration::Addon.new("SUSE_ADDON7", "12", "x86_64", depends_on: [addon3, addon6]) + describe "#selected" do + it "marks addon as selected" do + expect(Registration::Addon.selected.include?(addon)).to be_false + addon.selected + expect(Registration::Addon.selected.include?(addon)).to be_true + end - required_addons = addon7.required_addons - expect(required_addons.size).to eq(6) - expect(required_addons).to include(addon1, addon2, addon3, addon4, addon5, addon6) + it "adds to list of selected only one" do + addon.selected + addon.selected + expect(Registration::Addon.selected.count(addon)).to be 1 end end -end + describe "#unselected" do + it "marks addon as unselected" do + Registration::Addon.selected << addon + addon.unselected + expect(Registration::Addon.selected.include?(addon)).to be_false + end -describe Registration::AddonSorter do - describe ".registration_order" do - it "returns registration order according to the dependencies" do - addon1 = Registration::Addon.new("SUSE_ADDON1", "12", "x86_64") - addon2 = Registration::Addon.new("SUSE_ADDON2", "12", "x86_64") - addon3 = Registration::Addon.new("SUSE_ADDON3", "12", "x86_64", depends_on: [addon1, addon2]) - addon4 = Registration::Addon.new("SUSE_ADDON4", "12", "x86_64") - addon5 = Registration::Addon.new("SUSE_ADDON5", "12", "x86_64") - addon6 = Registration::Addon.new("SUSE_ADDON6", "12", "x86_64", depends_on: [addon4, addon5]) - addon7 = Registration::Addon.new("SUSE_ADDON7", "12", "x86_64", depends_on: [addon3, addon6]) - - # deliberately use an order which does not follow dependencies to make sure it is changed - addons = [addon7, addon2, addon3, addon5, addon4, addon6, addon1] - - solved = Registration::AddonSorter.registration_order(addons) - - # check the order, iterate over the list and check for missing dependencies - registered = [] - solved.each do |a| - # check that all dependendent add-ons are already registered - expect(a.depends_on - registered).to be_empty - registered << a - end - end - - it "raises KeyError exception when there is an unresolved dependency" do - addon1 = Registration::Addon.new("SUSE_ADDON1", "12", "x86_64") - addon2 = Registration::Addon.new("SUSE_ADDON3", "12", "x86_64", depends_on: [addon1]) + it "do nothing if addon is not selected" do + expect{addon.unselected}.to_not raise_error + end + end - expect{Registration::AddonSorter.registration_order([addon2])}.to raise_error(KeyError) + describe "#registered?" do + it "returns if addon is already registered" do + expect(addon.registered?).to be_false + Registration::Addon.registered << addon + expect(addon.registered?).to be_true end end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/test/factories.rb new/yast2-registration-3.1.69/test/factories.rb --- old/yast2-registration-3.1.65/test/factories.rb 1970-01-01 01:00:00.000000000 +0100 +++ new/yast2-registration-3.1.69/test/factories.rb 2014-06-10 11:13:03.000000000 +0200 @@ -0,0 +1,41 @@ +require "registration/addon" +require "suse/connect" + +def suse_connect_product_generator(attrs={}) + params = {} + params['name'] = attrs['name'] || "Product#{rand(100000)}" + params['long_name'] = attrs['long_name'] || "The best cool #{params['name']}" + params['description'] = attrs['description'] || "Bla bla bla bla!" + params['zypper_name'] = attrs['zypper_name'] || "prod#{rand(100000)}" + params['zypper_version'] = attrs['version'] || "#{rand(13)}" + params['arch'] = attrs['arch'] || "x86_64" + params['free'] = attrs.fetch('free', true) + params['eula_url'] = attrs['eula_url'] + params["extensions"] = attrs['extensions'] || [] + + params +end + +def addon_generator(params={}) + SUSE::Connect::Product.new(suse_connect_product_generator(params)) +end + +def addon_with_child_generator(parent_params={}) + prod_child = suse_connect_product_generator + SUSE::Connect::Product.new(suse_connect_product_generator(parent_params.merge('extensions' => [prod_child]))) +end + +# add cache reset, which is not needed in runtime, but for test it is critical +class Registration::Addon + class << self + def reset_cache + @cached_addons = nil + @registered = nil + @selected = nil + end + end +end + +def addon_reset_cache + Registration::Addon.reset_cache +end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/test/Makefile.am new/yast2-registration-3.1.69/test/Makefile.am --- old/yast2-registration-3.1.65/test/Makefile.am 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/test/Makefile.am 1970-01-01 01:00:00.000000000 +0100 @@ -1,17 +0,0 @@ -TESTS = \ - addon_spec.rb \ - discover_registration_services_test.rb \ - eula_downloader_spec.rb \ - helpers_spec.rb \ - import_certificate_dialog_test.rb \ - inst_scc_test.rb \ - registration_spec.rb \ - scc_test.rb \ - sw_mgmt_spec.rb - -TEST_FIXTURES = fixtures/test.pem - -TEST_EXTENSIONS = .rb -RB_LOG_COMPILER = rspec --format doc -VERBOSE = 1 -EXTRA_DIST = $(TESTS) $(TEST_FIXTURES) spec_helper.rb diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/yast2-registration-3.1.65/test/spec_helper.rb new/yast2-registration-3.1.69/test/spec_helper.rb --- old/yast2-registration-3.1.65/test/spec_helper.rb 2014-06-06 11:06:20.000000000 +0200 +++ new/yast2-registration-3.1.69/test/spec_helper.rb 2014-06-10 11:13:03.000000000 +0200 @@ -14,6 +14,7 @@ SimpleCov.start end + $:.unshift(File.expand_path("../../src/lib", __FILE__)) ENV["Y2DIR"] = File.expand_path("../../src", __FILE__) @@ -21,3 +22,6 @@ def fixtures_file(file) File.expand_path(File.join("../fixtures", file), __FILE__) end + +# load data generators +require_relative "factories" continue with "q"... Checked in at Tue Jun 10 15:14:50 CEST 2014 by bg Remember to have fun... -- To unsubscribe, e-mail: yast-commit+unsubscribe@opensuse.org For additional commands, e-mail: yast-commit+help@opensuse.org