Conversation
b08091a to
b78044d
Compare
In a distant past, the table to define a custom space policy could include partitions, full disks and other devices. Now it only displays the partitions of a given disk.
5dd143c to
3fef589
Compare
- Helper concept is not needed anymore. Each scope simply adds the functionality it needs.
Adapt issues
| config.alias | ||
| ), | ||
| kind: :partitioned_with_user | ||
| kind: IssueClasses::Config::OVERUSED |
There was a problem hiding this comment.
NP: overused sounds a bit strange. I kind of expect name like ALREADY_USED or IN_USE
| error( | ||
| format(_("There is no boot device with alias '%s'"), device_alias), | ||
| kind: :no_such_alias | ||
| kind: IssueClasses::Config::ALIAS |
There was a problem hiding this comment.
name is also a bit inconsistent. I kind of expect something like NO_ALIAS
There was a problem hiding this comment.
especially if you compare it with above NO_ROOT. I think issue should be either identified the part where is issue like ROOT, ALIAS, ENCRYPTION or by problem it describe like missing something, wrong entry, etc.
| # @see Base | ||
| def error(message) | ||
| super(message, kind: :search) | ||
| super(message, kind: IssueClasses::Config::SEARCH) |
There was a problem hiding this comment.
to be honest I am not sure on which level the issue classes acts...as here is generic search issue, but when alias is not found or root device is not found, it has dedicated entry. Overall I found it inconsistent in naming and in usage. For me if I need add new constant there, I will be lost how it should look like.
There was a problem hiding this comment.
You are right. There should be no generic classes. Each class should correspond to a well defined issue. I'm working on a PR to fix that.
| product?: Product; | ||
| l10n?: l10n.Config; | ||
| storage?: storage.Config; | ||
| product?: product.Config; |
There was a problem hiding this comment.
this looks strange. I think @imobachgs should probably check it as I kind of expect we should have soon proper type for product and software config here.
There was a problem hiding this comment.
Note that this PR does not define the new types related to sofware and products. It only places the existing types in the correct location. All those types will be revisited when adapting the sofware and product code to the new API.
There was a problem hiding this comment.
If it place the existing types in the correct location why product was removed from Config? I would expect some clarification somewhere because it is an storage PR but this is a product change.
| import { Issue } from "~/api/issue"; | ||
|
|
||
| function selectIssues(issues: Issue[]) { | ||
| return issues.filter((i: Issue) => i.scope === "storage" && i.class !== "proposal"); |
There was a problem hiding this comment.
I see this quite fragile comparison. When any new non config class will be added, then there will be problem. What about having prefixes in classes like config.no_root or config.label?
There was a problem hiding this comment.
Yes. That was my first thought. And I even proposed that to Imo and Iván.
But since using those prefixes is not a general idea used in other scopes and the comparison with "proposal" looked simpler, I decided to keep it simple.
I can bring back the original idea and add a "config" prefix.
| /** | ||
| * Model types. | ||
| * | ||
| * Types that extend the apiModel by adding calculated properties and methods. |
There was a problem hiding this comment.
I really dislike this...There is apiModel which is called model and here it defined another model which is extended version of model. This is extra confusing. I think it should really use different names like extendedModel or modelCalculated. In rust where it is easy to use namespace like proposal::Storage and system::Storage it is easy to have types which identical names, but in different namespace. But in typescript having types with identical name is quite hard to read the code, especially if they collide ( basically you always have to check imports in given file to see what it talks about ).
There was a problem hiding this comment.
The extended version of the model is going to dead. There will be only one model. Note that the changes in this PR are intended to make the code work with the new API, but all the bad designs are kept. Refactoring will come in another iteration.
dgdavid
left a comment
There was a problem hiding this comment.
Thanks for the extensive work on adapting the interface to the new API, @joseivanlopez!
I've reviewed the web part, but not in depth since I understand this is more of an adaptation rather than a full refactor, although some improvements have already been made 👌 Also, a big thanks to @jreidinger, who have done a more thorough review!
Overall it LGTM. I’ve added a few comments, some related to the changes here and some not. Feel free to consider them as feedback for thought if you think more changes are not actually not needed here.
| const keymaps = useSystem()?.keymaps; | ||
| const currentKeymap = useProposal()?.keymap; |
There was a problem hiding this comment.
I'm all for not opening discussions about enforcing strict conventions, specially considering that we don't have a formal style guide in place yet, However, I personally prefer to continue using destructuring where possible when it comes to extract data from hooks. It looks like the new useSystem hook might be returning_ undefined_, but I’m wondering if there's a (clean) way to avoid it and return an empty collection instead.
There was a problem hiding this comment.
Same applies for similar usage in other files in this PR.
There was a problem hiding this comment.
I am not sure if at some point we will need to distinguish between no data vs not fetched.
There was a problem hiding this comment.
Don't understand what you mean.
There was a problem hiding this comment.
If we always report data (e.g., {keymaps: []}, locales: []}), then we are not able to know if we have already fetched the data from the api or the data is not available yet. But as said, I don't know if we will need that.
| ...systemQuery, | ||
| select: selectSystem, | ||
| }); | ||
| return data; |
There was a problem hiding this comment.
This could be the place where return an empty object instead of undefined.
return data || {}There was a problem hiding this comment.
If we decide to always return a list, then I would move it to the select function.
|
|
||
| return client.onEvent((event) => { | ||
| if (event.type === "IssuesChanged") { | ||
| queryClient.invalidateQueries({ queryKey: ["issues"] }); |
There was a problem hiding this comment.
Not to be part of this PR, but we need to address the query keys thingy. Ideally, making it query export its id to be then reused. This would help to avoid typos in the future in a quite cheap way.
| queryClient.invalidateQueries({ queryKey: ["extendedConfig"] }); | ||
| queryClient.invalidateQueries({ queryKey: ["storageModel"] }); | ||
| queryClient.invalidateQueries({ queryKey: ["proposal"] }); |
There was a problem hiding this comment.
Not directly related to this PR, but when we tackle the queryKey thingy, we should consider following the recommendation for using query key factories (see https://tkdodo.eu/blog/effective-react-query-keys#use-query-key-factories, and #2447). By doing so, we could easily invalidate queries under the "proposal/" namespace without worrying about potential leftovers in the future.
There was a problem hiding this comment.
Yes, we should use some robust way for defining queries. But I think we will not have nested queries anymore.
There was a problem hiding this comment.
IMHO we have to take time to think about it. If these queries conceptually belongs to "proposal" I do not see a reason for not following key factory recommendation and put them under "proposal". It will make things better to work with.
There was a problem hiding this comment.
I don't get your point. Which queries do you think can be under proposal?
There was a problem hiding this comment.
Those you're invalidating here. The fact that you're invalidating them under certain event suggests that these queries could be grouped in some way. "Proposal" was just an example, but the key takeaway is that if you're frequently invalidating a set of queries together, they likely share a common parent or key.
| } | ||
|
|
||
| const solvedStorageModelQuery = (apiModel?: model.Config) => ({ | ||
| queryKey: ["solvedStorageModel", JSON.stringify(apiModel)], |
There was a problem hiding this comment.
Weird queryKey, not sure if we want to follow that path.
There was a problem hiding this comment.
This code is not new. Any suggestion?
There was a problem hiding this comment.
Not yet, as I do not have the full picture in mind at this time. Let's go ahead and change it when proceed.
| const systemQuery = { | ||
| queryKey: ["system"], | ||
| queryFn: getSystem, | ||
| }; |
There was a problem hiding this comment.
For a future PR,
| const systemQuery = { | |
| queryKey: ["system"], | |
| queryFn: getSystem, | |
| }; | |
| const KEY = "system"; | |
| const systemQuery = { | |
| queryKey: [KEY], | |
| queryFn: getSystem, | |
| }; |
and then export KEY.
a2eef54 to
fe8244e
Compare
| @@ -20,8 +20,18 @@ | |||
| * find current contact information at www.suse.com. | |||
| */ | |||
|
|
|||
| type Config = { | |||
There was a problem hiding this comment.
So, the file was removed here but not added in api/config/product.ts
…ge/ProposalPage (#2917) ## Problem There is a hook called `useConfigIssues` that is controversial (see for example #2902 (comment)). And, to be honest, ideally it should not be needed. The point is that the storage section may have a slightly different format (set of components) depending on quite specific logic. And that hook exists to support that, but... Why do we need a hook that is used in several parts of the application just because the storage page can have different formats? Because sadly the logic is spread along several components and files. ## Solution Centralize in a single `<ProposalPageContent>` component all decision making about which components will be rendered and about which issues will be listed. Now it is SO MUCH easier to follow the logic and to know what is going to be rendered. That allowed us to kill the `useConfigIssues` hook, now it's logic is used only once. No need to replicate the same criteria in several different places. **Bonus:** fixed an eslint-related comment that was leftover from some previous pull request (not sure when the comment became obsolete, but it raised a warning for me). ## Testing All the following combinations were tested manually and the result was the expected one. This should be converted into a unit test at some point. - Config is ok and supported by UI. Proposal worked. => ModelSection + ProposalResultSection - Config is ok and supported by UI. Proposal failed. => ProposalFailedInfo + ModelSection + ProposalResultSection - Config is ok but not supported by UI. Proposal worked. => UnsupportedModelInfo + ProposalResultSection - Config is ok but not supported by UI. Proposal failed. => UnknownConfigEmptyState - Config is wrong, supported by UI and fixable. No proposal tried. => FixableConfigInfo + ModelSection - Config is wrong, supported by UI but not fixable. No proposal tried. => InvalidConfigEmptyState - Config is wrong and not supported by UI. No proposal tried. => InvalidConfigEmptyState
## Problem We use the so-called classes to distinguish the different kind of Agama issues. As part of a recent pull request, the classification of the storage issues was revisited. But, as pointed by [this comment](#2902 (comment)), it was done in a sub-optimal way. The main problem with the list of classes after that pull request is that they have a different levels of abstraction. Some classes were quite generic (like "configEncryption" that was used for several different problems regarding encryption) while others identified very concrete situations (like "configNoRoot"). ## Solution Redefine the set of classes to be more consistent, without generic classes. ## Testing - Adapted unit tests - Tested manually ## Progress Still under development. So far, only the service was adapted.
Merge the new HTTP API. Each PR has been already reviewed, so it should be safe to merge it. * #1829 * #2508 * #2772 * #2826 * #2848 * #2860 * #2863 * #2866 * #2867 * #2869 * #2870 * #2871 * #2872 * #2873 * #2874 * #2875 * #2876 * #2877 * #2880 * #2881 * #2882 * #2884 * #2885 * #2886 * #2891 * #2892 * #2893 * #2894 * #2895 * #2896 * #2897 * #2898 * #2899 * #2900 * #2901 * #2902 * #2903 * #2904 * #2908 * #2909 * #2910 * #2912 * #2913 * #2914 * #2915 * #2916 * #2917 * #2918 * #2920 * #2921 * #2923 * #2924 * #2926 * #2928 * #2929 * #2930 * #2933 * #2934 * #2935 * #2936 * #2938 * #2939 * #2942 * #2943 * #2944 * #2945 * #2946 * #2947 * #2948 * #2950 * #2951 * #2952 * #2954 * #2955 * #2956 * #2957 * #2958 * #2959 * #2960 * #2961 * #2963 * #2964 * #2965 * #2967 * #2968 * #2969 * #2970 * #2971 * #2972 * #2974 * #2975 * #2977 * #2978 * #2980 * #2982 * #2983 * #2984 * #2988 * #2989 * #2991 * #2992 * #2993 * #2994 * #2995 * #2996 * #2997 * #2999
Prepare to release version 19. * #1829 * #2508 * #2772 * #2818 * #2826 * #2848 * #2860 * #2863 * #2864 * #2866 * #2867 * #2869 * #2870 * #2871 * #2872 * #2873 * #2874 * #2875 * #2876 * #2877 * #2880 * #2881 * #2882 * #2884 * #2885 * #2886 * #2891 * #2892 * #2893 * #2894 * #2895 * #2896 * #2897 * #2898 * #2899 * #2900 * #2901 * #2902 * #2903 * #2904 * #2908 * #2909 * #2910 * #2912 * #2913 * #2914 * #2915 * #2916 * #2917 * #2918 * #2920 * #2921 * #2923 * #2924 * #2926 * #2928 * #2929 * #2930 * #2933 * #2934 * #2935 * #2936 * #2937 * #2938 * #2939 * #2942 * #2943 * #2944 * #2945 * #2946 * #2947 * #2948 * #2949 * #2950 * #2951 * #2952 * #2954 * #2955 * #2956 * #2957 * #2958 * #2959 * #2960 * #2961 * #2963 * #2964 * #2965 * #2967 * #2968 * #2969 * #2970 * #2971 * #2972 * #2974 * #2975 * #2977 * #2978 * #2980 * #2981 * #2982 * #2983 * #2984 * #2988 * #2989 * #2990 * #2991 * #2992 * #2993 * #2994 * #2995 * #2996 * #2997 * #2998 * #2999 * #3000 * #3001 * #3002 * #3004 * #3005 * #3006 * #3007 * #3008 * #3009 * #3011 * #3012 * #3013 * #3014 * #3015 * #3016 * #3018 * #3019 * #3020 * #3021 * #3022 * #3023 * #3024 * #3025 * #3026 * #3027 * #3028 * #3029 * #3030 * #3031 * #3033 * #3034 * #3035 * #3036 * #3037 * #3039 * #3040 * #3041 * #3042 * #3043 * #3044 * #3045 * #3046 * #3047 * #3048 * #3049 * #3050 * #3051 * #3052 * #3053 * #3054 * #3055 * #3056 * #3057 * #3058 * #3060 * #3061 * #3062 * #3063 * #3064 * #3065 * #3066 * #3067 * #3068 * #3069 * #3070 * #3071 * #3072 * #3073 * #3074 * #3075 * #3076 * #3077 * #3078 * #3079 * #3086 * #3087 * #3088 * #3089 * #3090 * #3091 * #3092 * #3093 * #3094 * #3095 * #3096 * #3097 * #3098 * #3099 * #3100 * #3101 * #3102 * #3103 * #3104 * #3105 * #3106 * #3107 * #3108 * #3109 * #3110 * #3112 * #3113 * #3114 * #3115 * #3116 * #3117 * #3118 * #3119 * #3120 * #3122 * #3123 * #3124 * #3127 * #3128 * #3129 * #3130 * #3131 * #3133 * #3134 * #3135 * #3136 * #3137 * #3138 * #3139 * #3140 * #3141 * #3142 * #3143 * #3144 * #3145 * #3146 * #3147 * #3148 * #3149 * #3150 * #3151 * #3152 * #3153 * #3154 * #3155 * #3157 * #3158 * #3159 * #3160 * #3161 * #3162 * #3163 * #3164 * #3165 * #3166 * #3167 * #3168 * #3169 * #3170 * #3174 * #3175 * #3176 * #3177 * #3178 * #3179 * #3181 * #3182 * #3184 * #3185 * #3186 * #3188 * #3189 * #3190 * #3191 * #3192 * #3194 * #3195 * #3196 * #3197 * #3198 * #3199 * #3200 * #3201 * #3202 * #3203 * #3205 * #3206 * #3208 * #3209 * #3210 * #3213 * #3214 * #3215 * #3216 * #3217 * #3218 * #3219 * #3220 * #3222 * #3223 * #3224 * #3225 * #3226 * #3227 * #3228 * #3229 * #3230 * #3231 * #3232 * #3233 * #3234 * #3235 * #3236 * #3237 * #3238 * #3239 * #3240 * #3241 * #3242 * #3243 * #3244 * #3246 * #3247 * #3248 * #3250 * #3251 * #3252 * #3253 * #3254 * #3255 * #3256 * #3257 * #3258 * #3259 * #3260 * #3261 * #3262 * #3263 * #3265 * #3266 * #3267 * #3268 * #3269 * #3270 * #3271 * #3272 * #3273 * #3274 * #3275 * #3276 * #3277 * #3278 * #3279 * #3280 * #3281 * #3282 * #3283 * #3284 * #3285 * #3286 * #3287 * #3288 * #3289 * #3290 * #3291
Fix the storage UI after the migration to the new API.
Note: the failing tests will be adapted in a separate PR.