Skip to content

Commit fb940f9

Browse files
authored
Merge pull request #1421 from eduhub-org/fix/location-addresses-improvements
chore: Fix/location addresses improvements
2 parents 1540f61 + f43bbd1 commit fb940f9

File tree

68 files changed

+1782
-239
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

68 files changed

+1782
-239
lines changed

.cursor/rules/mobile-responsive-design.mdc

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -279,7 +279,15 @@ const MobilePagination: React.FC<PaginationProps> = ({
279279
}
280280

281281
// Full pagination for desktop
282-
return <FullPagination {...props} />;
282+
return (
283+
<FullPagination
284+
pageIndex={pageIndex}
285+
pageSize={pageSize}
286+
totalCount={totalCount}
287+
onPageChange={onPageChange}
288+
onPageSizeChange={onPageSizeChange}
289+
/>
290+
);
283291
};
284292
```
285293

backend/metadata/databases/default/tables/public_CourseLocation.yaml

Lines changed: 31 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,9 @@ object_relationships:
55
- name: Course
66
using:
77
foreign_key_constraint_on: courseId
8+
- name: DefaultSessionAddress
9+
using:
10+
foreign_key_constraint_on: defaultSessionAddressId
811
- name: LocationOption
912
using:
1013
manual_configuration:
@@ -18,15 +21,25 @@ insert_permissions:
1821
- role: instructor_access
1922
permission:
2023
check:
21-
Course:
22-
CourseInstructors:
23-
Expert:
24-
User:
25-
id:
26-
_eq: X-Hasura-User-Id
24+
_and:
25+
- Course:
26+
CourseInstructors:
27+
Expert:
28+
User:
29+
id:
30+
_eq: X-Hasura-User-Id
31+
- _or:
32+
- defaultSessionAddressId:
33+
_is_null: true
34+
- DefaultSessionAddress:
35+
locationOption:
36+
_ceq:
37+
- $
38+
- locationOption
2739
columns:
2840
- courseId
2941
- defaultSessionAddress
42+
- defaultSessionAddressId
3043
- id
3144
- locationOption
3245
select_permissions:
@@ -35,6 +48,7 @@ select_permissions:
3548
columns:
3649
- courseId
3750
- defaultSessionAddress
51+
- defaultSessionAddressId
3852
- id
3953
- locationOption
4054
filter: {}
@@ -45,6 +59,7 @@ select_permissions:
4559
- courseId
4660
- created_at
4761
- defaultSessionAddress
62+
- defaultSessionAddressId
4863
- id
4964
- locationOption
5065
- updated_at
@@ -56,6 +71,7 @@ update_permissions:
5671
columns:
5772
- courseId
5873
- defaultSessionAddress
74+
- defaultSessionAddressId
5975
- locationOption
6076
filter:
6177
Course:
@@ -64,7 +80,15 @@ update_permissions:
6480
User:
6581
id:
6682
_eq: X-Hasura-User-Id
67-
check: null
83+
check:
84+
_or:
85+
- defaultSessionAddressId:
86+
_is_null: true
87+
- DefaultSessionAddress:
88+
locationOption:
89+
_ceq:
90+
- $
91+
- locationOption
6892
delete_permissions:
6993
- role: instructor_access
7094
permission:

backend/metadata/databases/default/tables/public_LocationAddress.yaml

Lines changed: 60 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,15 @@ table:
44
object_relationships:
55
- name: LocationOption
66
using:
7-
foreign_key_constraint_on: locationOptionId
7+
foreign_key_constraint_on: locationOption
88
array_relationships:
9+
- name: CourseLocations
10+
using:
11+
foreign_key_constraint_on:
12+
column: defaultSessionAddressId
13+
table:
14+
name: CourseLocation
15+
schema: public
916
- name: SessionAddresses
1017
using:
1118
foreign_key_constraint_on:
@@ -14,11 +21,20 @@ array_relationships:
1421
name: SessionAddress
1522
schema: public
1623
insert_permissions:
24+
- role: admin
25+
permission:
26+
check: {}
27+
columns:
28+
- locationOption
29+
- shortLabel
30+
- address
31+
- description
32+
- aliases
1733
- role: instructor_access
1834
permission:
1935
check: {}
2036
columns:
21-
- locationOptionId
37+
- locationOption
2238
- shortLabel
2339
- address
2440
- description
@@ -27,17 +43,43 @@ insert_permissions:
2743
permission:
2844
check: {}
2945
columns:
30-
- locationOptionId
46+
- locationOption
3147
- shortLabel
3248
- address
3349
- description
3450
- aliases
3551
select_permissions:
52+
- role: admin
53+
permission:
54+
columns:
55+
- id
56+
- locationOption
57+
- shortLabel
58+
- address
59+
- description
60+
- aliases
61+
- created_at
62+
- updated_at
63+
filter: {}
64+
allow_aggregations: true
3665
- role: anonymous
3766
permission:
3867
columns:
3968
- id
40-
- locationOptionId
69+
- locationOption
70+
- shortLabel
71+
- address
72+
- description
73+
- aliases
74+
- created_at
75+
- updated_at
76+
filter: {}
77+
allow_aggregations: true
78+
- role: instructor_access
79+
permission:
80+
columns:
81+
- id
82+
- locationOption
4183
- shortLabel
4284
- address
4385
- description
@@ -50,7 +92,7 @@ select_permissions:
5092
permission:
5193
columns:
5294
- id
53-
- locationOptionId
95+
- locationOption
5496
- shortLabel
5597
- address
5698
- description
@@ -60,6 +102,16 @@ select_permissions:
60102
filter: {}
61103
allow_aggregations: true
62104
update_permissions:
105+
- role: admin
106+
permission:
107+
columns:
108+
- locationOption
109+
- shortLabel
110+
- address
111+
- description
112+
- aliases
113+
filter: {}
114+
check: {}
63115
- role: instructor_access
64116
permission:
65117
columns:
@@ -79,6 +131,9 @@ update_permissions:
79131
filter: {}
80132
check: {}
81133
delete_permissions:
134+
- role: admin
135+
permission:
136+
filter: {}
82137
- role: instructor_access
83138
permission:
84139
filter: {}

backend/metadata/databases/default/tables/public_LocationOption.yaml

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,13 @@ table:
33
schema: public
44
is_enum: true
55
array_relationships:
6+
- name: LocationAddresses
7+
using:
8+
foreign_key_constraint_on:
9+
column: locationOption
10+
table:
11+
name: LocationAddress
12+
schema: public
613
- name: Locations
714
using:
815
manual_configuration:
@@ -12,13 +19,6 @@ array_relationships:
1219
remote_table:
1320
name: CourseLocation
1421
schema: public
15-
- name: LocationAddresses
16-
using:
17-
foreign_key_constraint_on:
18-
column: locationOptionId
19-
table:
20-
name: LocationAddress
21-
schema: public
2222
select_permissions:
2323
- role: anonymous
2424
permission:

backend/metadata/databases/default/tables/public_SessionAddress.yaml

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,12 +5,12 @@ object_relationships:
55
- name: CourseLocation
66
using:
77
foreign_key_constraint_on: courseLocationId
8-
- name: Session
9-
using:
10-
foreign_key_constraint_on: sessionId
118
- name: LocationAddress
129
using:
1310
foreign_key_constraint_on: locationAddressId
11+
- name: Session
12+
using:
13+
foreign_key_constraint_on: sessionId
1414
insert_permissions:
1515
- role: instructor_access
1616
permission:
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
-- Rollback: Remove defaultSessionAddressId column from CourseLocation table
2+
3+
-- Drop the index first
4+
DROP INDEX IF EXISTS "public"."idx_course_location_default_session_address_id";
5+
6+
-- Drop the foreign key constraint (the column drop will cascade, but explicit is clearer)
7+
ALTER TABLE "public"."CourseLocation"
8+
DROP CONSTRAINT IF EXISTS "CourseLocation_defaultSessionAddressId_fkey";
9+
10+
-- Drop the column
11+
ALTER TABLE "public"."CourseLocation"
12+
DROP COLUMN IF EXISTS "defaultSessionAddressId";
13+
14+
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
-- Add defaultSessionAddressId column to CourseLocation table
2+
-- This field references LocationAddress for default session addresses
3+
4+
ALTER TABLE "public"."CourseLocation"
5+
ADD COLUMN "defaultSessionAddressId" integer;
6+
7+
-- Add foreign key constraint to ensure referential integrity
8+
ALTER TABLE "public"."CourseLocation"
9+
ADD CONSTRAINT "CourseLocation_defaultSessionAddressId_fkey"
10+
FOREIGN KEY ("defaultSessionAddressId") REFERENCES "public"."LocationAddress"("id")
11+
ON UPDATE RESTRICT ON DELETE SET NULL;
12+
13+
-- Create index to optimize queries on defaultSessionAddressId
14+
CREATE INDEX "idx_course_location_default_session_address_id"
15+
ON "public"."CourseLocation" ("defaultSessionAddressId");
16+
17+
COMMENT ON COLUMN "public"."CourseLocation"."defaultSessionAddressId" IS
18+
E'References a LocationAddress that serves as the default for sessions in this course location. Replaces the legacy text-based defaultSessionAddress field.';
19+
20+
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
-- Rollback the migration: Clear defaultSessionAddressId from CourseLocation
2+
-- Note: This doesn't delete the LocationAddress records to avoid data loss
3+
-- If you need to completely rollback, you should manually review and clean up LocationAddress table
4+
5+
UPDATE "public"."CourseLocation"
6+
SET "defaultSessionAddressId" = NULL
7+
WHERE "defaultSessionAddressId" IS NOT NULL;
8+
9+
-- Optionally, remove LocationAddress records that were created during this migration
10+
-- Uncomment the following lines if you want to remove migrated default addresses
11+
-- WARNING: This will permanently delete the migrated LocationAddress data
12+
13+
-- DELETE FROM "public"."LocationAddress"
14+
-- WHERE "description" = 'Migrated from CourseLocation.defaultSessionAddress';
15+
16+
DO $$ BEGIN
17+
RAISE NOTICE 'Migration rollback completed. CourseLocation.defaultSessionAddressId set to NULL.';
18+
RAISE NOTICE 'LocationAddress records were NOT deleted to preserve data integrity.';
19+
RAISE NOTICE 'Review and manually clean up LocationAddress table if needed.';
20+
END $$;
21+
22+
Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
-- Migrate default session addresses from CourseLocation to LocationAddress
2+
-- This migration creates LocationAddress records for defaultSessionAddress values
3+
-- and updates CourseLocation to reference the new LocationAddress records
4+
5+
-- Step 1: Insert unique default session addresses into LocationAddress table
6+
-- Only create entries for non-empty defaultSessionAddress values
7+
INSERT INTO "public"."LocationAddress" (
8+
"locationOptionId",
9+
"shortLabel",
10+
"address",
11+
"description"
12+
)
13+
SELECT DISTINCT
14+
cl."locationOption",
15+
-- Generate a short label from the first few words or first line of the address
16+
CASE
17+
WHEN LENGTH(cl."defaultSessionAddress") <= 50 THEN cl."defaultSessionAddress"
18+
WHEN POSITION(E'\n' in cl."defaultSessionAddress") > 0 AND POSITION(E'\n' in cl."defaultSessionAddress") <= 50
19+
THEN LEFT(cl."defaultSessionAddress", POSITION(E'\n' in cl."defaultSessionAddress") - 1)
20+
WHEN POSITION(' ' in SUBSTRING(cl."defaultSessionAddress" FROM 45)) > 0
21+
THEN LEFT(cl."defaultSessionAddress", 44 + POSITION(' ' in SUBSTRING(cl."defaultSessionAddress" FROM 45)))
22+
ELSE LEFT(cl."defaultSessionAddress", 50) || '...'
23+
END,
24+
cl."defaultSessionAddress",
25+
'Migrated from CourseLocation.defaultSessionAddress'
26+
FROM "public"."CourseLocation" cl
27+
WHERE cl."defaultSessionAddress" IS NOT NULL
28+
AND cl."defaultSessionAddress" != ''
29+
AND cl."locationOption" IS NOT NULL
30+
-- Avoid creating duplicates if the exact same address already exists
31+
AND NOT EXISTS (
32+
SELECT 1 FROM "public"."LocationAddress" la
33+
WHERE la."locationOptionId" = cl."locationOption"
34+
AND la."address" = cl."defaultSessionAddress"
35+
)
36+
ON CONFLICT ("locationOptionId", "shortLabel") DO NOTHING;
37+
38+
-- Step 2: Update CourseLocation records to reference the new LocationAddress entries
39+
UPDATE "public"."CourseLocation" cl
40+
SET "defaultSessionAddressId" = la.id
41+
FROM "public"."LocationAddress" la
42+
WHERE cl."locationOption" = la."locationOptionId"
43+
AND cl."defaultSessionAddress" = la."address"
44+
AND cl."defaultSessionAddress" IS NOT NULL
45+
AND cl."defaultSessionAddress" != '';
46+
47+
-- Report migration statistics
48+
DO $$
49+
DECLARE
50+
total_course_locations INTEGER;
51+
migrated_defaults INTEGER;
52+
created_default_addresses INTEGER;
53+
BEGIN
54+
SELECT COUNT(*) INTO total_course_locations
55+
FROM "public"."CourseLocation"
56+
WHERE "defaultSessionAddress" IS NOT NULL AND "defaultSessionAddress" != '';
57+
58+
SELECT COUNT(*) INTO migrated_defaults
59+
FROM "public"."CourseLocation"
60+
WHERE "defaultSessionAddressId" IS NOT NULL;
61+
62+
SELECT COUNT(*) INTO created_default_addresses
63+
FROM "public"."LocationAddress"
64+
WHERE "description" = 'Migrated from CourseLocation.defaultSessionAddress';
65+
66+
RAISE NOTICE 'Default session address migration completed:';
67+
RAISE NOTICE ' CourseLocations with defaultSessionAddress: %', total_course_locations;
68+
RAISE NOTICE ' Migrated to defaultSessionAddressId: %', migrated_defaults;
69+
RAISE NOTICE ' LocationAddress records created: %', created_default_addresses;
70+
END $$;
71+
72+

0 commit comments

Comments
 (0)