Skip to content

Commit

Permalink
Merge pull request #814 from openSUSE/registration-ui
Browse files Browse the repository at this point in the history
Registration UI
  • Loading branch information
joseivanlopez committed Nov 15, 2023
2 parents d9556cb + f6d5bfe commit a165dd3
Show file tree
Hide file tree
Showing 45 changed files with 2,162 additions and 628 deletions.
10 changes: 0 additions & 10 deletions products.d/ALP-Dolomite.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -15,16 +15,6 @@ translations:
bezpečnost pro poskytování úplného minima ke spuštění úloh a služeb v
kontejnerech nebo virtuálních strojích.
software:
installation_repositories:
- url: https://updates.suse.com/SUSE/Products/ALP-Dolomite/1.0/x86_64/product/
archs: x86_64
- url: https://updates.suse.com/SUSE/Products/ALP-Dolomite/1.0/aarch64/product/
archs: aarch64
- url: https://updates.suse.com/SUSE/Products/ALP-Dolomite/1.0/s390x/product/
archs: s390
- url: https://updates.suse.com/SUSE/Products/ALP-Dolomite/1.0/ppc64le/product/
archs: ppc

mandatory_patterns:
- alp_base_zypper
- alp_cockpit
Expand Down
8 changes: 8 additions & 0 deletions service/lib/agama/dbus/software/product.rb
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,10 @@ def requirement

# Tries to register with the given registration code.
#
# @note Software is not automatically probed after registering the product. The reason is
# to avoid dealing with possible probing issues in the registration D-Bus API. Clients
# have to explicitly call to #Probe after registering a product.
#
# @param reg_code [String]
# @param email [String, nil]
#
Expand Down Expand Up @@ -174,6 +178,10 @@ def register(reg_code, email: nil)

# Tries to deregister.
#
# @note Software is not automatically probed after deregistering the product. The reason is
# to avoid dealing with possible probing issues in the deregistration D-Bus API. Clients
# have to explicitly call to #Probe after deregistering a product.
#
# @return [Array(Integer, String)] Result code and a description.
# Possible result codes:
# 0: success
Expand Down
11 changes: 1 addition & 10 deletions service/lib/agama/software/manager.rb
Original file line number Diff line number Diff line change
Expand Up @@ -286,16 +286,7 @@ def used_disk_space
end

def registration
return @registration if @registration

@registration = Registration.new(self, @logger)
@registration.on_change do
# reprobe and repropose when system is register or deregistered
probe
proposal
end

@registration
@registration ||= Registration.new(self, logger)
end

# code is based on https://github.com/yast/yast-registration/blob/master/src/lib/registration/sw_mgmt.rb#L365
Expand Down
4 changes: 2 additions & 2 deletions service/test/agama/software/manager_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -191,7 +191,7 @@
stub_const("Agama::Software::Manager::REPOS_DIR", repos_dir)
stub_const("Agama::Software::Manager::REPOS_BACKUP", backup_repos_dir)
FileUtils.mkdir_p(repos_dir)
subject.select_product("ALP-Dolomite")
subject.select_product("Tumbleweed")
end

after do
Expand All @@ -218,7 +218,7 @@
end

it "registers the repository from config" do
expect(repositories).to receive(:add).with(/Dolomite/)
expect(repositories).to receive(:add).with(/tumbleweed/)
expect(repositories).to receive(:load)
subject.probe
end
Expand Down
6 changes: 2 additions & 4 deletions web/src/App.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import { Outlet } from "react-router-dom";

import { _ } from "~/i18n";
import { useInstallerClient, useInstallerClientStatus } from "~/context/installer";
import { useSoftware } from "./context/software";
import { useProduct } from "./context/product";
import { STARTUP, INSTALL } from "~/client/phase";
import { BUSY } from "~/client/status";

Expand All @@ -39,7 +39,6 @@ import {
ShowTerminalButton,
Sidebar
} from "~/components/core";
import { ChangeProductLink } from "~/components/software";
import { LanguageSwitcher } from "./components/l10n";
import { Layout, Loading, Title } from "./components/layout";
import { useL10n } from "./context/l10n";
Expand All @@ -57,7 +56,7 @@ const ATTEMPTS = 3;
function App() {
const client = useInstallerClient();
const { attempt } = useInstallerClientStatus();
const { products } = useSoftware();
const { products } = useProduct();
const { language } = useL10n();
const [status, setStatus] = useState(undefined);
const [phase, setPhase] = useState(undefined);
Expand Down Expand Up @@ -107,7 +106,6 @@ function App() {
<>
<Sidebar>
<div className="flex-stack">
<ChangeProductLink />
<IssuesLink />
<Disclosure label={_("Diagnostic tools")} data-keep-sidebar-open>
<ShowLogButton />
Expand Down
6 changes: 3 additions & 3 deletions web/src/App.test.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -31,9 +31,9 @@ jest.mock("~/client");

// list of available products
let mockProducts;
jest.mock("~/context/software", () => ({
...jest.requireActual("~/context/software"),
useSoftware: () => {
jest.mock("~/context/product", () => ({
...jest.requireActual("~/context/product"),
useProduct: () => {
return {
products: mockProducts,
selectedProduct: null
Expand Down
4 changes: 4 additions & 0 deletions web/src/assets/styles/utilities.scss
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,10 @@
padding: 0;
}

.p-0 {
padding: 0;
}

.no-stack-gutter {
--stack-gutter: 0;
}
Expand Down
66 changes: 55 additions & 11 deletions web/src/client/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,29 +30,41 @@ import { UsersClient } from "./users";
import phase from "./phase";
import { QuestionsClient } from "./questions";
import { NetworkClient } from "./network";
import { IssuesClient } from "./issues";
import cockpit from "../lib/cockpit";

const BUS_ADDRESS_FILE = "/run/agama/bus.address";
const MANAGER_SERVICE = "org.opensuse.Agama.Manager1";

/**
* @typedef {object} InstallerClient
* @property {LanguageClient} language - language client
* @property {ManagerClient} manager - manager client
* @property {Monitor} monitor - service monitor
* @property {NetworkClient} network - network client
* @property {SoftwareClient} software - software client
* @property {StorageClient} storage - storage client
* @property {UsersClient} users - users client
* @property {QuestionsClient} questions - questions client
* @property {IssuesClient} issues - issues client
* @property {LanguageClient} language - language client.
* @property {ManagerClient} manager - manager client.
* @property {Monitor} monitor - service monitor.
* @property {NetworkClient} network - network client.
* @property {SoftwareClient} software - software client.
* @property {StorageClient} storage - storage client.
* @property {UsersClient} users - users client.
* @property {QuestionsClient} questions - questions client.
* @property {() => Promise<Issues>} issues - issues from all contexts.
* @property {(handler: IssuesHandler) => (() => void)} onIssuesChange - registers a handler to run
* when issues from any context change. It returns a function to deregister the handler.
* @property {() => Promise<boolean>} isConnected - determines whether the client is connected
* @property {(handler: () => void) => (() => void)} onDisconnect - registers a handler to run
* when the connection is lost. It returns a function to deregister the
* handler.
*/

/**
* @typedef {import ("~/client/mixins").Issue} Issue
*
* @typedef {object} Issues
* @property {Issue[]} [product] - Issues from product.
* @property {Issue[]} [storage] - Issues from storage.
* @property {Issue[]} [software] - Issues from software.
*
* @typedef {(issues: Issues) => void} IssuesHandler
*/

/**
* Creates the Agama client
*
Expand All @@ -67,7 +79,38 @@ const createClient = (address = "unix:path=/run/agama/bus") => {
const storage = new StorageClient(address);
const users = new UsersClient(address);
const questions = new QuestionsClient(address);
const issues = new IssuesClient({ storage });

/**
* Gets all issues, grouping them by context.
*
* TODO: issues are requested by several components (e.g., overview sections, notifications
* provider, issues page, storage page, etc). There should be an issues provider.
*
* @returns {Promise<Issues>}
*/
const issues = async () => {
return {
product: await software.product.getIssues(),
storage: await storage.getIssues(),
software: await software.getIssues()
};
};

/**
* Registers a callback to be executed when issues change.
*
* @param {IssuesHandler} handler - Callback function.
* @return {() => void} - Function to deregister the callback.
*/
const onIssuesChange = (handler) => {
const unsubscribeCallbacks = [];

unsubscribeCallbacks.push(software.product.onIssuesChange(i => handler({ product: i })));
unsubscribeCallbacks.push(storage.onIssuesChange(i => handler({ storage: i })));
unsubscribeCallbacks.push(software.onIssuesChange(i => handler({ software: i })));

return () => { unsubscribeCallbacks.forEach(cb => cb()) };
};

const isConnected = async () => {
try {
Expand All @@ -88,6 +131,7 @@ const createClient = (address = "unix:path=/run/agama/bus") => {
users,
questions,
issues,
onIssuesChange,
isConnected,
onDisconnect: (handler) => monitor.onDisconnect(handler)
};
Expand Down
78 changes: 0 additions & 78 deletions web/src/client/issues.js

This file was deleted.

Loading

0 comments on commit a165dd3

Please sign in to comment.