Reassign product interiors (#355)
This commit is contained in:
@@ -0,0 +1,331 @@
|
|||||||
|
-- Reassign product interior assignments based on rules by Malin from
|
||||||
|
-- https://nordicetrade-my.sharepoint.com/:x:/g/personal/malin_photowall_se/EaGIC8JX5KlBsI90kreSMX0B4wBRAsjL1ghDN8DQ0waQNw?e=GV93tN
|
||||||
|
--
|
||||||
|
-- Using the rules below, we will convert the percentages into ranges that we can match against:
|
||||||
|
-- (50%, 50%) => (1-50, 51-100), (100% => 1-100), (20%, 40%, 40%) => (1-20, 21-60, 61-100), etc
|
||||||
|
--
|
||||||
|
-- We then assign a random number between 1 and 100 to every product interior we have that uses the old rooms.
|
||||||
|
--
|
||||||
|
-- The random number determines which new room to use, and we update accordingly.
|
||||||
|
-- It will not create a 100% perfect distribution, but acceptable for our purpose.
|
||||||
|
-- If you modify this script according to comments at the end, you will see a debug output of the results.
|
||||||
|
--
|
||||||
|
-- One situation had not been anticipated: sometimes we try to create a print product-room combo that already existed.
|
||||||
|
-- Either because it was already assigned before running the script, or because two rules assigned the same new room
|
||||||
|
-- to a print product. Because of the late realization, this is handled at the end (by ignoring one of them),
|
||||||
|
-- skewing the percentages a bit.
|
||||||
|
--
|
||||||
|
--
|
||||||
|
-- The rules:
|
||||||
|
--
|
||||||
|
-- Interiors that should be replaced completely (assign 100% to new room/s):
|
||||||
|
-- old interior => new rooms (100% if not specified)
|
||||||
|
-- room01_wallpaper_landscape => 103
|
||||||
|
-- room02_wallpaper_landscape => 84 (50%), 88 (50%)
|
||||||
|
-- room03_wallpaper_landscape => 75
|
||||||
|
-- room04_wallpaper_landscape => 91
|
||||||
|
-- room05_wallpaper_landscape => 84
|
||||||
|
-- room06_wallpaper_landscape => 71
|
||||||
|
-- room07_wallpaper_landscape => 76
|
||||||
|
-- room08_wallpaper_landscape => 103
|
||||||
|
-- room09_wallpaper_landscape => 84
|
||||||
|
-- room10_wallpaper_landscape => 85
|
||||||
|
-- room11_wallpaper_landscape => 88
|
||||||
|
-- room12_wallpaper_landscape => 84
|
||||||
|
-- room36_wallpaper_landscape => 82
|
||||||
|
-- room37_wallpaper_landscape => 85
|
||||||
|
-- room54_wallpaper_landscape => 105
|
||||||
|
-- room58_wallpaper_landscape => 93
|
||||||
|
-- room59_wallpaper_landscape => 105
|
||||||
|
--
|
||||||
|
-- Interiors that should be partially replaced
|
||||||
|
-- room38_wallpaper_landscape => 87 (30%), 111 (30%), 100 (20%), self (20%)
|
||||||
|
-- room41_wallpaper_landscape => 88 (50%), 99 (20%), self (30%)
|
||||||
|
-- room43_wallpaper_landscape => 92 (20%), 90 (20%), 91 (10%), self (50%)
|
||||||
|
-- room44_wallpaper_landscape => 103 (50%), self (50%)
|
||||||
|
-- room46_wallpaper_landscape => 87 (30%), 85 (30%), self (40%)
|
||||||
|
-- room47_wallpaper_landscape => 89 (40%), 102 (20%), self (40%)
|
||||||
|
-- room48_wallpaper_landscape => 89 (40%), 86 (20%), 106 (10%), self (30%)
|
||||||
|
-- room49_wallpaper_landscape => 112 (10%), 107 (10%), 108 (10%), self (70%)
|
||||||
|
-- room50_wallpaper_landscape => 70 (20%), 75 (20%), 76 (20%), 74 (10%), self (30%)
|
||||||
|
-- room51_wallpaper_landscape => 77 (20%), 78 (20%), 79 (20%), self (40%)
|
||||||
|
-- room52_wallpaper_landscape => 76 (50%), self (50%)
|
||||||
|
-- room53_wallpaper_landscape => 72 (30%), 71 (30%), self (40%)
|
||||||
|
-- room55_wallpaper_landscape => 80 (50%), self (50%)
|
||||||
|
-- room57_wallpaper_landscape => 98 (50%), self (50%)
|
||||||
|
-- room61_wallpaper_landscape => 83 (30%), 105 (30%), 104 (10%), self (30%)
|
||||||
|
-- room62_wallpaper_landscape => 94 (30%), 96 (30%), 101 (20%), self (20%)
|
||||||
|
-- room63_wallpaper_landscape => 97 (50%), self (50%)
|
||||||
|
-- room64_wallpaper_landscape => 95 (50%), self (50%)
|
||||||
|
-- room69_wallpaper_landscape => 73 (30%), 81 (30%), self (40%)
|
||||||
|
--
|
||||||
|
--
|
||||||
|
--
|
||||||
|
-- STEP 1: Store the rules in a table (using a real table instead of a temporary table to allow foreign keys)
|
||||||
|
drop table if exists temp_interiors_to_change;
|
||||||
|
create table temp_interiors_to_change (
|
||||||
|
old_room_number int references rooms (id) not null,
|
||||||
|
new_room_number int references rooms (id) not null,
|
||||||
|
percentage int not null check(percentage >= 1 and percentage <=100),
|
||||||
|
unique(old_room_number, new_room_number)
|
||||||
|
);
|
||||||
|
insert into temp_interiors_to_change(old_room_number, new_room_number, percentage) values
|
||||||
|
(1, 103, 100),
|
||||||
|
(2, 84, 50),
|
||||||
|
(2, 88, 50),
|
||||||
|
(3, 75, 100),
|
||||||
|
(4, 91, 100),
|
||||||
|
(5, 84, 100),
|
||||||
|
(6, 71, 100),
|
||||||
|
(7, 76, 100),
|
||||||
|
(8, 103, 100),
|
||||||
|
(9, 84, 100),
|
||||||
|
(10, 85, 100),
|
||||||
|
(11, 88, 100),
|
||||||
|
(12, 84, 100),
|
||||||
|
(36, 82, 100),
|
||||||
|
(37, 85, 100),
|
||||||
|
(54, 105, 100),
|
||||||
|
(58, 93, 100),
|
||||||
|
(59, 105, 100),
|
||||||
|
(38, 87, 30),
|
||||||
|
(38, 111, 30),
|
||||||
|
(38, 100, 20),
|
||||||
|
(38, 38, 20),
|
||||||
|
(41, 88, 50),
|
||||||
|
(41, 99, 20),
|
||||||
|
(41, 41, 30),
|
||||||
|
(43, 92, 20),
|
||||||
|
(43, 90, 20),
|
||||||
|
(43, 91, 10),
|
||||||
|
(43, 43, 50),
|
||||||
|
(44, 103, 50),
|
||||||
|
(44, 44, 50),
|
||||||
|
(46, 87, 30),
|
||||||
|
(46, 85, 30),
|
||||||
|
(46, 46, 40),
|
||||||
|
(47, 89, 40),
|
||||||
|
(47, 102, 20),
|
||||||
|
(47, 47, 40),
|
||||||
|
(48, 89, 40),
|
||||||
|
(48, 86, 20),
|
||||||
|
(48, 106, 10),
|
||||||
|
(48, 48, 30),
|
||||||
|
(49, 112, 10),
|
||||||
|
(49, 107, 10),
|
||||||
|
(49, 108, 10),
|
||||||
|
(49, 49, 70),
|
||||||
|
(50, 70, 20),
|
||||||
|
(50, 75, 20),
|
||||||
|
(50, 76, 20),
|
||||||
|
(50, 74, 10),
|
||||||
|
(50, 50, 30),
|
||||||
|
(51, 77, 20),
|
||||||
|
(51, 78, 20),
|
||||||
|
(51, 79, 20),
|
||||||
|
(51, 51, 40),
|
||||||
|
(52, 76, 50),
|
||||||
|
(52, 52, 50),
|
||||||
|
(53, 72, 30),
|
||||||
|
(53, 71, 30),
|
||||||
|
(53, 53, 40),
|
||||||
|
(55, 80, 50),
|
||||||
|
(55, 55, 50),
|
||||||
|
(57, 98, 50),
|
||||||
|
(57, 57, 50),
|
||||||
|
(61, 83, 30),
|
||||||
|
(61, 105, 30),
|
||||||
|
(61, 104, 10),
|
||||||
|
(61, 61, 30),
|
||||||
|
(62, 94, 30),
|
||||||
|
(62, 96, 30),
|
||||||
|
(62, 101, 20),
|
||||||
|
(62, 62, 20),
|
||||||
|
(63, 97, 50),
|
||||||
|
(63, 63, 50),
|
||||||
|
(64, 95, 50),
|
||||||
|
(64, 64, 50),
|
||||||
|
(69, 73, 30),
|
||||||
|
(69, 81, 30),
|
||||||
|
(69, 69, 40)
|
||||||
|
;
|
||||||
|
|
||||||
|
-- STEP 2. Add an internal number 1-4 for each new room assigned to an old room
|
||||||
|
-- with_internal_ids:
|
||||||
|
-- old_room_number | new_room_number | percentage | internal_id
|
||||||
|
-- -----------------+-----------------+------------+-------------
|
||||||
|
-- 1 | 103 | 100 | 1
|
||||||
|
-- 2 | 84 | 50 | 1
|
||||||
|
-- 2 | 88 | 50 | 2
|
||||||
|
-- 37 | 85 | 100 | 1
|
||||||
|
-- 38 | 38 | 20 | 1
|
||||||
|
-- 38 | 87 | 30 | 2
|
||||||
|
-- 38 | 100 | 20 | 3
|
||||||
|
-- 38 | 111 | 30 | 4
|
||||||
|
with with_internal_ids as (
|
||||||
|
select *,
|
||||||
|
(row_number() over (partition by old_room_number)) as internal_id
|
||||||
|
from temp_interiors_to_change order by 1
|
||||||
|
),
|
||||||
|
-- STEP 3. Calculate the start and end numbers for each room, based on its percentage on how much it should be used
|
||||||
|
-- with_start_and_end_numbers:
|
||||||
|
-- old_room_number | new_room_number | percentage | internal_id | start_number | up_to
|
||||||
|
-- -----------------+-----------------+------------+-------------+--------------+-------
|
||||||
|
-- 1 | 103 | 100 | 1 | 1 | 100
|
||||||
|
-- 2 | 84 | 50 | 1 | 1 | 50
|
||||||
|
-- 2 | 88 | 50 | 2 | 51 | 100
|
||||||
|
-- 37 | 85 | 100 | 1 | 1 | 100
|
||||||
|
-- 38 | 38 | 20 | 1 | 1 | 20
|
||||||
|
-- 38 | 87 | 30 | 2 | 21 | 50
|
||||||
|
-- 38 | 100 | 20 | 3 | 51 | 70
|
||||||
|
-- 38 | 111 | 30 | 4 | 71 | 100
|
||||||
|
-- 41 | 41 | 30 | 1 | 1 | 30
|
||||||
|
with_start_number as (
|
||||||
|
select
|
||||||
|
*,
|
||||||
|
(select coalesce(sum(percentage), 0) + 1 start_number from with_internal_ids wii
|
||||||
|
where wii.old_room_number = main.old_room_number
|
||||||
|
and wii.new_room_number <> main.new_room_number
|
||||||
|
and wii.internal_id < main.internal_id)
|
||||||
|
from
|
||||||
|
with_internal_ids main
|
||||||
|
),
|
||||||
|
with_start_and_end_numbers as (
|
||||||
|
select
|
||||||
|
*,
|
||||||
|
(100 - (100 - percentage) + start_number - 1) as up_to
|
||||||
|
from with_start_number
|
||||||
|
),
|
||||||
|
-- STEP 4. Add the database ids for the rooms. (i.e. room01_wallpaper_landscape is actually id 4 in rooms table)
|
||||||
|
-- room_ids:
|
||||||
|
-- old_room_no | old_room_id | new_no | new_room_id | percentage | start_number | up_to
|
||||||
|
-- -------------+-------------+--------+-------------+------------+--------------+-------
|
||||||
|
-- 1 | 4 | 103 | 332 | 100 | 1 | 100
|
||||||
|
-- 2 | 8 | 84 | 313 | 50 | 1 | 50
|
||||||
|
-- 2 | 8 | 88 | 317 | 50 | 51 | 100
|
||||||
|
-- 38 | 243 | 38 | 243 | 20 | 1 | 20
|
||||||
|
-- 38 | 243 | 87 | 316 | 30 | 21 | 50
|
||||||
|
-- 38 | 243 | 100 | 329 | 20 | 51 | 70
|
||||||
|
-- 38 | 243 | 111 | 340 | 30 | 71 | 100
|
||||||
|
room_ids as (
|
||||||
|
select
|
||||||
|
t.old_room_number old_room_no,
|
||||||
|
(select id from rooms where name = 'room' || (CASE WHEN old_room_number < 10 THEN '0' ELSE '' END)
|
||||||
|
|| old_room_number ||'_wallpaper_landscape' limit 1) as old_room_id,
|
||||||
|
t.new_room_number new_no,
|
||||||
|
(select id from rooms where name = 'room' || (CASE WHEN new_room_number < 10 THEN '0' ELSE '' END)
|
||||||
|
|| new_room_number ||'_wallpaper_landscape' limit 1) as new_room_id,
|
||||||
|
t.percentage,
|
||||||
|
start_number,
|
||||||
|
up_to
|
||||||
|
from
|
||||||
|
with_start_and_end_numbers t
|
||||||
|
),
|
||||||
|
-- STEP 5. Select all current product interiors that use the old rooms, and assign each a random number 1-100.
|
||||||
|
-- affected_interiors:
|
||||||
|
-- id | room_id | random1to100
|
||||||
|
-- --------+---------+--------------
|
||||||
|
-- 528448 | 255 | 31
|
||||||
|
-- 536310 | 264 | 1
|
||||||
|
-- 505329 | 264 | 39
|
||||||
|
-- 505327 | 280 | 8
|
||||||
|
-- 522889 | 255 | 86
|
||||||
|
-- 539476 | 252 | 98
|
||||||
|
-- 580142 | 261 | 4
|
||||||
|
-- 562716 | 252 | 58
|
||||||
|
-- 580143 | 248 | 71
|
||||||
|
affected_interiors as (
|
||||||
|
select id, room_id,
|
||||||
|
(floor((random() * 100)) + 1) random1to100
|
||||||
|
from interiors
|
||||||
|
where interiors.room_id in (select distinct old_room_id from room_ids)
|
||||||
|
),
|
||||||
|
-- STEP 6. Add which new room the old interior should get, by matching the random number against the start_number and up_to
|
||||||
|
-- interiors_to_potentially_be_updated:
|
||||||
|
-- interior_id | current_room_id | new_room_id
|
||||||
|
-- -------------+-----------------+-------------
|
||||||
|
-- 528448 | 255 | 255
|
||||||
|
-- 536310 | 264 | 264
|
||||||
|
-- 505329 | 264 | 264
|
||||||
|
-- 505327 | 280 | 300
|
||||||
|
-- 522889 | 255 | 255
|
||||||
|
-- 539476 | 252 | 319
|
||||||
|
interiors_to_potentially_update as (
|
||||||
|
select
|
||||||
|
affected_interiors.id interior_id,
|
||||||
|
affected_interiors.room_id current_room_id,
|
||||||
|
(select new_room_id from room_ids where affected_interiors.room_id = room_ids.old_room_id
|
||||||
|
and random1to100 >= start_number and random1to100 <= up_to limit 1)
|
||||||
|
from
|
||||||
|
affected_interiors
|
||||||
|
), with_print_ids as (
|
||||||
|
select interiors_to_potentially_update.*, interiors.print_id
|
||||||
|
from interiors_to_potentially_update
|
||||||
|
join interiors on interiors.id = interiors_to_potentially_update.interior_id
|
||||||
|
),
|
||||||
|
-- Workaround to handle case where two rules assign the same new room to a print product (will cause error).
|
||||||
|
-- It has to be filtered out before the UPDATE statement, so we give each row a number, and then only select one of them.
|
||||||
|
-- interior_id | current_room_id | new_room_id | print_id | duplicate_order_number
|
||||||
|
-- -------------+-----------------+-------------+----------+------------------------
|
||||||
|
-- 767310 | 290 | 290 | 189915 | 1
|
||||||
|
-- 767311 | 283 | 334 | 189915 | 1
|
||||||
|
-- 767315 | 288 | 334 | 189915 | 2
|
||||||
|
ranked_to_update as (
|
||||||
|
select *, row_number() over (partition by print_id, new_room_id order by interior_id) as duplicate_order_number
|
||||||
|
from with_print_ids
|
||||||
|
), final_update as (
|
||||||
|
select interior_id, current_room_id, new_room_id
|
||||||
|
from ranked_to_update where duplicate_order_number = 1
|
||||||
|
)
|
||||||
|
|
||||||
|
-- -- FINAL STEP: Update interiors:
|
||||||
|
UPDATE interiors SET room_id = to_update.new_room_id
|
||||||
|
FROM final_update to_update
|
||||||
|
WHERE interiors.id = to_update.interior_id AND to_update.current_room_id <> to_update.new_room_id
|
||||||
|
AND NOT EXISTS (
|
||||||
|
-- This prevents errors if the printproduct was already assigned to the new room, prior to running the script
|
||||||
|
SELECT 1 FROM interiors existing WHERE existing.print_id = interiors.print_id
|
||||||
|
AND existing.room_id = to_update.new_room_id AND existing.id <> interiors.id
|
||||||
|
);
|
||||||
|
-- Remove any interiors that were to be 100% replaced, but that we had to ignore due to duplicates
|
||||||
|
delete from interiors where room_id in (
|
||||||
|
select id from rooms where name in ('room01_wallpaper_landscape', 'room02_wallpaper_landscape', 'room03_wallpaper_landscape',
|
||||||
|
'room04_wallpaper_landscape', 'room05_wallpaper_landscape', 'room06_wallpaper_landscape', 'room07_wallpaper_landscape',
|
||||||
|
'room08_wallpaper_landscape', 'room09_wallpaper_landscape', 'room10_wallpaper_landscape', 'room11_wallpaper_landscape',
|
||||||
|
'room12_wallpaper_landscape', 'room36_wallpaper_landscape', 'room37_wallpaper_landscape', 'room54_wallpaper_landscape',
|
||||||
|
'room58_wallpaper_landscape', 'room59_wallpaper_landscape')
|
||||||
|
);
|
||||||
|
DROP TABLE temp_interiors_to_change;
|
||||||
|
|
||||||
|
|
||||||
|
-- VERIFICATION/CODE REVIEW: Delete lines 289-305, and uncomment remaining sql below to see example results
|
||||||
|
-- , debug_count_assinged_rooms as (
|
||||||
|
-- select current_room_id, new_room_id, count(*) as assigned_count
|
||||||
|
-- -- from interiors_to_potentially_update group by 1,2
|
||||||
|
-- from final_update group by 1,2
|
||||||
|
-- ), debug_count_total as (
|
||||||
|
-- select d.*,
|
||||||
|
-- -- (select count(*) from interiors_to_potentially_update i where i.current_room_id = d.current_room_id) as total_count
|
||||||
|
-- (select count(*) from final_update i where i.current_room_id = d.current_room_id) as total_count
|
||||||
|
-- from debug_count_assinged_rooms d
|
||||||
|
-- ), debug_compare as (
|
||||||
|
-- select
|
||||||
|
-- r.old_room_no old_room_number,
|
||||||
|
-- r.new_no new_room_number,
|
||||||
|
-- r.percentage specified_percentage_for_new_room,
|
||||||
|
-- assigned_count assigned_count_new_room,
|
||||||
|
-- total_count total_count_old_room,
|
||||||
|
-- round((assigned_count*100.0 / total_count), 2) as assigned_percentage,
|
||||||
|
-- round((assigned_count*100.0 / total_count), 2) - percentage as diff_vs_specification
|
||||||
|
-- from
|
||||||
|
-- room_ids r
|
||||||
|
-- left join debug_count_total d on r.old_room_id = d.current_room_id and r.new_room_id = d.new_room_id
|
||||||
|
-- ) select * from debug_compare order by 1,2;
|
||||||
|
-- -- debug_compare:
|
||||||
|
-- -- old_room_number | new_room_number | specified_percentage_for_new_room | assigned_count_new_room | total_count_old_room | assigned_percentage | diff_vs_specification
|
||||||
|
-- -- -----------------+-----------------+-----------------------------------+-------------------------+----------------------+---------------------+-----------------------
|
||||||
|
-- -- 1 | 103 | 100 | 10 | 10 | 100.00 | 0.00
|
||||||
|
-- -- 2 | 84 | 50 | 753 | 1456 | 51.72 | 1.72
|
||||||
|
-- -- 2 | 88 | 50 | 703 | 1456 | 48.28 | -1.72
|
||||||
|
-- -- 3 | 75 | 100 | 3 | 3 | 100.00 | 0.00
|
||||||
|
-- -- 4 | 91 | 100 | 4 | 4 | 100.00 | 0.00
|
||||||
Reference in New Issue
Block a user