Skip to content

Commit

Permalink
Merge branch 'SLE-15-SP5' into merge-SLE-15-SP5
Browse files Browse the repository at this point in the history
  • Loading branch information
imobachgs committed Jun 8, 2023
2 parents 90a504a + 75d88c3 commit 71fa473
Show file tree
Hide file tree
Showing 4 changed files with 127 additions and 7 deletions.
7 changes: 7 additions & 0 deletions package/yast2-users.changes
Original file line number Diff line number Diff line change
@@ -1,3 +1,10 @@
-------------------------------------------------------------------
Wed Jun 7 16:22:59 UTC 2023 - Imobach Gonzalez Sosa <igonzalezsosa@suse.com>

- Write the users when using AutoYaST on an installed system
(bsc#1211753).
- 4.6.2

-------------------------------------------------------------------
Thu Mar 23 14:04:54 UTC 2023 - Ancor Gonzalez Sosa <ancor@suse.com>

Expand Down
2 changes: 1 addition & 1 deletion package/yast2-users.spec
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@


Name: yast2-users
Version: 4.6.1
Version: 4.6.2
Release: 0
Summary: YaST2 - User and Group Configuration
License: GPL-2.0-only
Expand Down
51 changes: 45 additions & 6 deletions src/lib/users/clients/auto.rb
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,10 @@
require "y2users"
require "y2users/autoinst/reader"
require "y2issues"
require "y2users/config_merger"
require "y2users/config_manager"
require "y2users/autoinst/reader"
require "y2users/linux/writer"

Yast.import "Users"
Yast.import "Linuxrc"
Expand Down Expand Up @@ -90,15 +94,33 @@ def read
end

# @note This code is not executed during autoinstallation (instead, the
# users_finish is used). However, it is used when running ayast_setup.
# users_finish is used). However, it is used when running ayast_setup
# or using the AutoYaST UI.
#
# When working on an already installed system, the process of detecting
# which users/groups changed is tricky:
#
# * The approach followed by [Y2Users::UsersModule::Reader](https://github.com/yast/yast-users/blob/414b6c7373068c367c0a01be20a1399fbd0ef470/src/lib/y2users/users_module/reader.rb#L103),
# checking the content of `org_user`, does not work because it is defined
# only if the user was modified using the AutoYaST UI.
# * Directly comparing the users/groups from `system_config` and
# `target_config` does not work because passwords are missing from the
# `target_config` users.
#
# To overcome these limitations, we only consider those users/groups
# which 'modified' property is not nil, although it does not guarantee
# that they changed at all.
#
# @return [Boolean] true if configuration was changed; false otherwise.
def write
Yast::Users.SetWriteOnly(true)
progress_orig = Yast::Progress.set(false)
ret = Yast::Users.Write == ""
Yast::Progress.set(progress_orig)
ret
system_config = Y2Users::ConfigManager.instance.system(force_read: true)
new_config = system_config.copy
_, target_config = Y2Users::UsersModule::Reader.new.read
remove_unchanged_elements(target_config)
Y2Users::ConfigMerger.new(new_config, target_config).merge
writer = Y2Users::Linux::Writer.new(new_config, system_config)
issues = writer.write
issues.empty?
end

def modified?
Expand Down Expand Up @@ -149,6 +171,23 @@ def read_linuxrc_root_pwd(config)

root_user
end

# Clean users and groups that have not changed according to the 'modified' attributes
#
# @param config [Y2Users::Config] Configuration to clean
def remove_unchanged_elements(config)
all_users = Yast::Users.GetUsers("uid", "local").values +
Yast::Users.GetUsers("uid", "system").values
uids = all_users.select { |u| u["modified"] }.map { |u| u["uid"] }
users = config.users.reject { |u| uids.include?(u.name) }

all_groups = Yast::Users.GetGroups("cn", "local").values +
Yast::Users.GetGroups("cn", "system").values
gids = all_groups.select { |g| g["modified"] }.map { |g| g["cn"] }
groups = config.groups.reject { |g| gids.include?(g.name) }

(users + groups).each { |e| config.detach(e) }
end
end
end
end
74 changes: 74 additions & 0 deletions test/lib/users/clients/auto_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -208,5 +208,79 @@
subject.run
end
end

context "Write" do
let(:func) { "Write" }
let(:reader) do
instance_double(
Y2Users::UsersModule::Reader, read: [Y2Users::Config.new, target_config]
)
end
let(:writer) { instance_double(Y2Users::Linux::Writer, write: []) }
let(:system_config) { Y2Users::Config.new }
let(:target_config) do
Y2Users::Config.new.tap do |config|
config.attach(user)
config.attach(root)
config.attach(users_group)
config.attach(others_group)
end
end
let(:root) { Y2Users::User.new("root").tap { |u| u.uid = 0 } }
let(:user) { Y2Users::User.new("foo") }
let(:users_group) { Y2Users::Group.new("users") }
let(:others_group) { Y2Users::Group.new("others") }

before do
allow(Y2Users::ConfigManager.instance).to receive(:system)
.and_return(system_config)
allow(Y2Users::Linux::Writer).to receive(:new).and_return(writer)
allow(Y2Users::UsersModule::Reader).to receive(:new).and_return(reader)
allow(Yast::Users).to receive(:GetUsers).with("uid", "local")
.and_return("foo" => { "uid" => "foo", "modified" => true })
allow(Yast::Users).to receive(:GetUsers).with("uid", "system")
.and_return("root" => { "uid" => "root", "modified" => false })
allow(Yast::Users).to receive(:GetGroups).with("cn", "local")
.and_return("foo" => { "cn" => "users", "modified" => true })
allow(Yast::Users).to receive(:GetGroups).with("cn", "system")
.and_return("root" => { "cn" => "others", "modified" => false })
end

it "writes the users defined in the Users module" do
expect(Y2Users::Linux::Writer).to receive(:new) do |new_config, _|
names = new_config.users.map(&:name)
expect(names).to include("foo")
expect(names).to_not include("root")
writer
end
subject.run
end

it "writes the groups defined in the Users module" do
expect(Y2Users::Linux::Writer).to receive(:new) do |new_config, _|
names = new_config.groups.map(&:name)
expect(names).to include("users")
expect(names).to_not include("others")
writer
end
subject.run
end

context "when there are not issues" do
it "returns true" do
expect(subject.run).to eq(true)
end
end

context "when any issue was found" do
before do
allow(writer).to receive(:write).and_return([double("issue")])
end

it "returns false" do
expect(subject.run).to eq(false)
end
end
end
end
end

0 comments on commit 71fa473

Please sign in to comment.