Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
32 commits
Select commit Hold shift + click to select a range
cf9fb11
[service] Add a method to validate the users service
imobachgs Nov 9, 2022
a453b91
[service] Add a D-Bus Validation1 interface
imobachgs Nov 10, 2022
a75cae3
[service] Add a WithValidation mixin for clients
imobachgs Nov 10, 2022
baf216f
[service] Add validation to the users service
imobachgs Nov 10, 2022
67be61f
[web] Add a WithValidation mixin
imobachgs Nov 10, 2022
2aa4481
[web] Extend the UsersClient with validation
imobachgs Nov 10, 2022
1102718
[service] Add a CanInstall method the manager service
imobachgs Nov 10, 2022
f33ed95
[web] Add a canInstall function to ManagerClient
imobachgs Nov 10, 2022
a9df5ab
[web] Fix a typo in mixins.js
imobachgs Nov 10, 2022
e001025
[web] Display validation errors
imobachgs Nov 10, 2022
adc9616
[service] Do not install if the configuration is not valid
imobachgs Nov 10, 2022
ccd17f7
[service] Add validation to the storage service
imobachgs Nov 10, 2022
2a9509d
[web] Extend the StorageClient with validation
imobachgs Nov 10, 2022
134db17
[web] Use the validation mechanism to handle storage errors
imobachgs Nov 10, 2022
90a7313
[service] Make RuboCop happy
imobachgs Nov 10, 2022
e99e0a7
[web] Fix pop-up title when cannot install
imobachgs Nov 11, 2022
cc304ea
[service] Rename IsValid to Valid
imobachgs Nov 11, 2022
dac7a48
[service] Describe the Validation1 interface.
imobachgs Nov 11, 2022
2c6530c
[web] Add type annotations to the installer client
imobachgs Nov 11, 2022
50d58cb
[web] Move InstallButton to its own file
imobachgs Nov 11, 2022
1dc3aac
[web] Rewrite the component to show validation errors
imobachgs Nov 11, 2022
4fc8db1
[web] Use ValidationErrors in users and storage sections
imobachgs Nov 11, 2022
b902536
[web] Remove the old errors list
imobachgs Nov 11, 2022
27f5d12
[web] Extend Storage component unit tests
imobachgs Nov 13, 2022
c3eab71
[web] Fix InstallButton text
imobachgs Nov 13, 2022
5d7f758
[web] Improve the presentation of validation errors
imobachgs Nov 13, 2022
4cdc27a
[service] Improve the "missing user/root password" error
imobachgs Nov 13, 2022
0ef1b41
[service] Rename ValidationErrors to Errors
imobachgs Nov 14, 2022
d4bc7cf
[web] Rename ValidationErrors to Errors
imobachgs Nov 14, 2022
14f0233
Merge branch 'master' into pre-install-checks
imobachgs Nov 14, 2022
0a282d4
Merge branch 'master' into pre-install-checks
imobachgs Nov 14, 2022
93b99e8
[service] Fix dbus/storage/proposal tests
imobachgs Nov 14, 2022
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 15 additions & 1 deletion doc/dbus_api.md
Original file line number Diff line number Diff line change
Expand Up @@ -305,6 +305,20 @@ The main object of a service implements the following interface:
- Finished: b (r)
Whether the progress has finished.

## Validation

The main object of a service may implement the validation interface. It reports
any issue that might block the installation.

### org.opensuse.DInstaller.Validation1

- Errors: array of strings (as)
List of validation errors.

- Valid: boolean (b)
Whether there are validation errors. It is a way to check whether a service
is ready for installation without having to retrieve the list of errors.

## Manager

### Installation Phases
Expand Down Expand Up @@ -365,4 +379,4 @@ reason, the *manager* service will store the status of each service and the clie

- BusyServices -> a(s) (r)

List of names of the currently busy services.
List of names of the currently busy services.
3 changes: 0 additions & 3 deletions service/Gemfile.lock
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,3 @@ DEPENDENCIES
simplecov (~> 0.21.2)
simplecov-lcov (~> 0.8.0)
yard (~> 0.9.0)

BUNDLED WITH
2.3.3
2 changes: 2 additions & 0 deletions service/lib/dinstaller/dbus/clients/storage.rb
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
require "dinstaller/dbus/clients/base"
require "dinstaller/dbus/clients/with_service_status"
require "dinstaller/dbus/clients/with_progress"
require "dinstaller/dbus/clients/with_validation"

module DInstaller
module DBus
Expand All @@ -30,6 +31,7 @@ module Clients
class Storage < Base
include WithServiceStatus
include WithProgress
include WithValidation

PROPOSAL_IFACE = "org.opensuse.DInstaller.Storage.Proposal1"
private_constant :PROPOSAL_IFACE
Expand Down
2 changes: 2 additions & 0 deletions service/lib/dinstaller/dbus/clients/users.rb
Original file line number Diff line number Diff line change
Expand Up @@ -21,13 +21,15 @@

require "dinstaller/dbus/clients/base"
require "dinstaller/dbus/clients/with_service_status"
require "dinstaller/dbus/clients/with_validation"

module DInstaller
module DBus
module Clients
# D-Bus client for users configuration
class Users < Base
include WithServiceStatus
include WithValidation

def initialize
super
Expand Down
48 changes: 48 additions & 0 deletions service/lib/dinstaller/dbus/clients/with_validation.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
# frozen_string_literal: true

# Copyright (c) [2022] SUSE LLC
#
# All Rights Reserved.
#
# This program is free software; you can redistribute it and/or modify it
# under the terms of version 2 of the GNU General Public License as published
# by the Free Software Foundation.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
# more details.
#
# You should have received a copy of the GNU General Public License along
# with this program; if not, contact SUSE LLC.
#
# To contact SUSE LLC about this file by physical or electronic mail, you may
# find current contact information at www.suse.com.

require "dinstaller/validation_error"

module DInstaller
module DBus
# Mixin to include in the clients of services that implement the Validation1 interface
module WithValidation
VALIDATION_IFACE = "org.opensuse.DInstaller.Validation1"
private_constant :VALIDATION_IFACE

# Returns the validation errors
#
# @return [Array<ValidationError>] Validation errors
def errors
dbus_object[VALIDATION_IFACE]["Errors"].map do |message|
DInstaller::ValidationError.new(message)
end
end

# Determines whether the service settings are valid or not
#
# @return [Boolean] true if the service has valid data; false otherwise
def valid?
dbus_object[VALIDATION_IFACE]["Valid"]
end
end
end
end
92 changes: 92 additions & 0 deletions service/lib/dinstaller/dbus/interfaces/validation.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
# frozen_string_literal: true

# Copyright (c) [2022] SUSE LLC
#
# All Rights Reserved.
#
# This program is free software; you can redistribute it and/or modify it
# under the terms of version 2 of the GNU General Public License as published
# by the Free Software Foundation.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
# more details.
#
# You should have received a copy of the GNU General Public License along
# with this program; if not, contact SUSE LLC.
#
# To contact SUSE LLC about this file by physical or electronic mail, you may
# find current contact information at www.suse.com.

require "dbus"

module DInstaller
module DBus
module Interfaces
# Mixin to define the Validation D-Bus interface
#
# @example Update the validation on a D-Bus call
# class Backend
# def validate
# ["Some error"]
# end
# end
#
# class Demo < DInstaller::DBus::BaseObject
# include DInstaller::DBus::Interfaces::Validation
#
# dbus_interface "org.opensuse.DInstaller.Demo1" do
# dbus_reader :errors, "as", dbus_name: "Errors"
# dbus_method :Foo, "out result:u" do
# # do some stuff
# update_validation # run this method is the validation can change
# 0
# end
# end
# end
#
# @note This mixin is expected to be included in a class that inherits from {DBus::BaseObject}
# and it requires a #backend method that returns an object that implements a #validate method.
module Validation
VALIDATION_INTERFACE = "org.opensuse.DInstaller.Validation1"

# D-Bus properties of the Validation1 interface
#
# @return [Hash]
def validation_properties
interfaces_and_properties[VALIDATION_INTERFACE]
end

# Updates the validation and raise the `PropertiesChanged` signal
def update_validation
@errors = nil
dbus_properties_changed(VALIDATION_INTERFACE, validation_properties, [])
end

# Returns the validation errors
#
# @return [Array<String>] Validation error messages
def errors
@errors ||= backend.validate.map(&:message)
end

# Determines whether the service settings are valid or not
#
# @return [Boolean] true if the service has valid data; false otherwise
def valid?
errors.empty?
end

def self.included(base)
base.class_eval do
dbus_interface VALIDATION_INTERFACE do
dbus_reader :errors, "as", dbus_name: "Errors"
dbus_reader :valid?, "b", dbus_name: "Valid"
end
end
end
end
end
end
end
10 changes: 10 additions & 0 deletions service/lib/dinstaller/dbus/manager.rb
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ def initialize(backend, logger)
dbus_interface MANAGER_INTERFACE do
dbus_method(:Probe, "") { config_phase }
dbus_method(:Commit, "") { install_phase }
dbus_method(:CanInstall, "out result:b") { can_install? }
dbus_reader :installation_phases, "aa{sv}"
dbus_reader :current_installation_phase, "u"
dbus_reader :busy_services, "as"
Expand All @@ -73,11 +74,20 @@ def config_phase

# Runs the install phase
def install_phase
raise ::DBus::Error, "Installation settings are invalid" unless backend.valid?

safe_run do
busy_while { backend.install_phase }
end
end

# Determines whether the installation can start
#
# @return [Boolean]
def can_install?
backend.valid?
end

# Description of all possible installation phase values
#
# @return [Array<Hash>]
Expand Down
7 changes: 7 additions & 0 deletions service/lib/dinstaller/dbus/storage/manager.rb
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
require "dinstaller/dbus/with_service_status"
require "dinstaller/dbus/interfaces/progress"
require "dinstaller/dbus/interfaces/service_status"
require "dinstaller/dbus/interfaces/validation"

module DInstaller
module DBus
Expand All @@ -33,6 +34,7 @@ class Manager < BaseObject
include WithServiceStatus
include Interfaces::Progress
include Interfaces::ServiceStatus
include Interfaces::Validation

PATH = "/org/opensuse/DInstaller/Storage1"
private_constant :PATH
Expand All @@ -44,6 +46,7 @@ class Manager < BaseObject
def initialize(backend, logger)
super(PATH, logger: logger)
@backend = backend
register_proposal_callbacks
register_progress_callbacks
register_service_status_callbacks
end
Expand Down Expand Up @@ -73,6 +76,10 @@ def finish

# @return [DInstaller::Software::Manager]
attr_reader :backend

def register_proposal_callbacks
backend.proposal.on_calculate { update_validation }
end
end
end
end
Expand Down
4 changes: 1 addition & 3 deletions service/lib/dinstaller/dbus/storage/proposal.rb
Original file line number Diff line number Diff line change
Expand Up @@ -94,9 +94,7 @@ def available_devices
#
# @return [Array<String>]
def candidate_devices
return [] unless backend.settings

backend.settings.candidate_devices
backend.candidate_devices
end

# Whether the proposal creates logical volumes
Expand Down
7 changes: 7 additions & 0 deletions service/lib/dinstaller/dbus/users.rb
Original file line number Diff line number Diff line change
Expand Up @@ -24,13 +24,15 @@
require "dinstaller/dbus/base_object"
require "dinstaller/dbus/with_service_status"
require "dinstaller/dbus/interfaces/service_status"
require "dinstaller/dbus/interfaces/validation"

module DInstaller
module DBus
# YaST D-Bus object (/org/opensuse/DInstaller/Users1)
class Users < BaseObject
include WithServiceStatus
include Interfaces::ServiceStatus
include Interfaces::Validation

PATH = "/org/opensuse/DInstaller/Users1"
private_constant :PATH
Expand Down Expand Up @@ -64,6 +66,7 @@ def initialize(backend, logger)
backend.assign_root_password(value, encrypted)

dbus_properties_changed(USERS_INTERFACE, { "RootPasswordSet" => !value.empty? }, [])
update_validation
0
end

Expand All @@ -73,6 +76,7 @@ def initialize(backend, logger)

dbus_properties_changed(USERS_INTERFACE, { "RootPasswordSet" => backend.root_password? },
[])
update_validation
0
end

Expand All @@ -81,6 +85,7 @@ def initialize(backend, logger)
backend.root_ssh_key = (value)

dbus_properties_changed(USERS_INTERFACE, { "RootSSHKey" => value }, [])
update_validation
0
end

Expand All @@ -90,6 +95,7 @@ def initialize(backend, logger)
backend.assign_first_user(full_name, user_name, password, auto_login, data)

dbus_properties_changed(USERS_INTERFACE, { "FirstUser" => first_user }, [])
update_validation
0
end

Expand All @@ -98,6 +104,7 @@ def initialize(backend, logger)
backend.remove_first_user

dbus_properties_changed(USERS_INTERFACE, { "FirstUser" => first_user }, [])
update_validation
0
end

Expand Down
7 changes: 7 additions & 0 deletions service/lib/dinstaller/manager.rb
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,13 @@ def on_services_status_change(&block)
service_status_recorder.on_service_status_change(&block)
end

# Determines whether the configuration is valid and the system is ready for installation
#
# @return [Boolean]
def valid?
[storage, users].all?(&:valid?)
end

private

attr_reader :config
Expand Down
7 changes: 7 additions & 0 deletions service/lib/dinstaller/storage/manager.rb
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,13 @@ def proposal
@proposal ||= Proposal.new(logger, config)
end

# Validates the storage configuration
#
# @return [Array<ValidationError>] List of validation errors
def validate
proposal.validate
end

private

PROPOSAL_ID = "storage_proposal"
Expand Down
Loading