introduce-separate-database-schema-hs-office-and-amend-generators (#105)

Co-authored-by: Michael Hoennig <michael@hoennig.de>
Reviewed-on: #105
Reviewed-by: Marc Sandlus <marc.sandlus@hostsharing.net>
This commit is contained in:
Michael Hoennig 2024-09-18 10:28:21 +02:00
parent 285e6fbeb5
commit 23b60641e3
91 changed files with 1015 additions and 1002 deletions

View File

@ -206,14 +206,14 @@ Limit (cost=6549.08..6549.35 rows=54 width=16)
```SQL
SELECT hore1_0.uuid,a1_0.uuid,a1_0.familyname,a1_0.givenname,a1_0.persontype,a1_0.salutation,a1_0.title,a1_0.tradename,a1_0.version,c1_0.uuid,c1_0.caption,c1_0.emailaddresses,c1_0.phonenumbers,c1_0.postaladdress,c1_0.version,h1_0.uuid,h1_0.familyname,h1_0.givenname,h1_0.persontype,h1_0.salutation,h1_0.title,h1_0.tradename,h1_0.version,hore1_0.mark,hore1_0.type,hore1_0.version
FROM hs_office_relation_rv hore1_0
LEFT JOIN hs_office_person_rv a1_0 ON a1_0.uuid=hore1_0.anchoruuid
LEFT JOIN hs_office_contact_rv c1_0 ON c1_0.uuid=hore1_0.contactuuid
LEFT JOIN hs_office_person_rv h1_0 ON h1_0.uuid=hore1_0.holderuuid
FROM hs_office.relation_rv hore1_0
LEFT JOIN hs_office.person_rv a1_0 ON a1_0.uuid=hore1_0.anchoruuid
LEFT JOIN hs_office.contact_rv c1_0 ON c1_0.uuid=hore1_0.contactuuid
LEFT JOIN hs_office.person_rv h1_0 ON h1_0.uuid=hore1_0.holderuuid
WHERE hore1_0.uuid=$1
```
That query on the `hs_office_relation_rv`-table joins the three references anchor-person, holder-person and contact.
That query on the `hs_office.relation_rv`-table joins the three references anchor-person, holder-person and contact.
### Total-Query-Time > Total-Import-Runtime
@ -270,16 +270,16 @@ At this point, the import took 21mins with these statistics:
| query | calls | total_m | mean_ms |
|-------|-------|---------|---------|
| select hore1_0.uuid,a1_0.uuid,a1_0.familyname,a1_0.givenname,a1_0.persontype,a1_0.salutation,a1_0.title,a1_0.tradename,a1_0.version,c1_0.uuid,c1_0.caption,c1_0.emailaddresses,c1_0.phonenumbers,c1_0.postaladdress, c1_0.version,h1_0.uuid,h1_0.familyname,h1_0.givenname,h1_0.persontype,h1_0.salutation,h1_0.title,h1_0.tradename,h1_0.version,hore1_0.mark,hore1_0.type,hore1_0.version from public.hs_office_relation_rv hore1_0 left join public.hs_office_person_rv a1_0 on a1_0.uuid=hore1_0.anchoruuid left join public.hs_office_contact_rv c1_0 on c1_0.uuid=hore1_0.contactuuid left join public.hs_office_person_rv h1_0 on h1_0.uuid=hore1_0.holderuuid where hore1_0.uuid=$1 | 517 | 11 | 1282 |
| select hope1_0.uuid,hope1_0.familyname,hope1_0.givenname,hope1_0.persontype,hope1_0.salutation,hope1_0.title,hope1_0.tradename,hope1_0.version from public.hs_office_person_rv hope1_0 where hope1_0.uuid=$1 | 973 | 4 | 254 |
| select hoce1_0.uuid,hoce1_0.caption,hoce1_0.emailaddresses,hoce1_0.phonenumbers,hoce1_0.postaladdress,hoce1_0.version from public.hs_office_contact_rv hoce1_0 where hoce1_0.uuid=$1 | 973 | 4 | 253 |
| select hore1_0.uuid,a1_0.uuid,a1_0.familyname,a1_0.givenname,a1_0.persontype,a1_0.salutation,a1_0.title,a1_0.tradename,a1_0.version,c1_0.uuid,c1_0.caption,c1_0.emailaddresses,c1_0.phonenumbers,c1_0.postaladdress, c1_0.version,h1_0.uuid,h1_0.familyname,h1_0.givenname,h1_0.persontype,h1_0.salutation,h1_0.title,h1_0.tradename,h1_0.version,hore1_0.mark,hore1_0.type,hore1_0.version from public.hs_office.relation_rv hore1_0 left join public.hs_office.person_rv a1_0 on a1_0.uuid=hore1_0.anchoruuid left join public.hs_office.contact_rv c1_0 on c1_0.uuid=hore1_0.contactuuid left join public.hs_office.person_rv h1_0 on h1_0.uuid=hore1_0.holderuuid where hore1_0.uuid=$1 | 517 | 11 | 1282 |
| select hope1_0.uuid,hope1_0.familyname,hope1_0.givenname,hope1_0.persontype,hope1_0.salutation,hope1_0.title,hope1_0.tradename,hope1_0.version from public.hs_office.person_rv hope1_0 where hope1_0.uuid=$1 | 973 | 4 | 254 |
| select hoce1_0.uuid,hoce1_0.caption,hoce1_0.emailaddresses,hoce1_0.phonenumbers,hoce1_0.postaladdress,hoce1_0.version from public.hs_office.contact_rv hoce1_0 where hoce1_0.uuid=$1 | 973 | 4 | 253 |
| call rbac.grantRoleToRole(roleUuid, superRoleUuid, superRoleDesc.assumed) | 31316 | 0 | 1 |
| call buildRbacSystemForHsHostingAsset(NEW) | 2258 | 0 | 7 |
| select * from rbac.isGranted(array[granteeId], grantedId) | 44613 | 0 | 0 |
| insert into public.hs_hosting_asset_rv (alarmcontactuuid,assignedtoassetuuid,bookingitemuuid,caption,config,identifier,parentassetuuid,type,version,uuid) values ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10) | 2207 | 0 | 7 |
| insert into hs_hosting_asset (alarmcontactuuid, version, bookingitemuuid, type, parentassetuuid, assignedtoassetuuid, config, uuid, identifier, caption) values (new.alarmcontactuuid, new. version, new. bookingitemuuid, new. type, new. parentassetuuid, new. assignedtoassetuuid, new. config, new. uuid, new. identifier, new. caption) returning * | 2207 | 0 | 7 |
| insert into public.hs_office_relation_rv (anchoruuid,contactuuid,holderuuid,mark,type,version,uuid) values ($1,$2,$3,$4,$5,$6,$7) | 1261 | 0 | 9 |
| insert into hs_office_relation (uuid, version, anchoruuid, holderuuid, contactuuid, type, mark) values (new.uuid, new. version, new. anchoruuid, new. holderuuid, new. contactuuid, new. type, new. mark) returning * | 1261 | 0 | 9 |
| insert into public.hs_office.relation_rv (anchoruuid,contactuuid,holderuuid,mark,type,version,uuid) values ($1,$2,$3,$4,$5,$6,$7) | 1261 | 0 | 9 |
| insert into hs_office.relation (uuid, version, anchoruuid, holderuuid, contactuuid, type, mark) values (new.uuid, new. version, new. anchoruuid, new. holderuuid, new. contactuuid, new. type, new. mark) returning * | 1261 | 0 | 9 |
| call buildRbacSystemForHsOfficeRelation(NEW) | 1276 | 0 | 8 |
| with recursive grants as ( select descendantUuid, ascendantUuid from RbacGrants where descendantUuid = grantedId union all select ""grant"".descendantUuid, ""grant"".ascendantUuid from RbacGrants ""grant"" inner join grants recur on recur.ascendantUuid = ""grant"".descendantUuid ) select exists ( select $3 from grants where ascendantUuid = any(granteeIds) ) or grantedId = any(granteeIds) | 47540 | 0 | 0 |
| insert into RbacGrants (grantedByTriggerOf, ascendantuuid, descendantUuid, assumed) values (currentTriggerObjectUuid(), superRoleId, subRoleId, doAssume) on conflict do nothing" | 40472 | 0 | 0 |
@ -294,17 +294,17 @@ We changed these mappings from `EAGER` (default) to `LAZY` to `@ManyToOne(fetch
:::small
| query | calls | total (min) | mean (ms) |
|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------|-------------|----------|
| select hope1_0.uuid,hope1_0.familyname,hope1_0.givenname,hope1_0.persontype,hope1_0.salutation,hope1_0.title,hope1_0.tradename,hope1_0.version from public.hs_office_person_rv hope1_0 where hope1_0.uuid=$1 | 1015 | 4 | 238 |
| select hore1_0.uuid,hore1_0.anchoruuid,hore1_0.contactuuid,hore1_0.holderuuid,hore1_0.mark,hore1_0.type,hore1_0.version from public.hs_office_relation_rv hore1_0 where hore1_0.uuid=$1 | 517 | 4 | 439 |
| select hoce1_0.uuid,hoce1_0.caption,hoce1_0.emailaddresses,hoce1_0.phonenumbers,hoce1_0.postaladdress,hoce1_0.version from public.hs_office_contact_rv hoce1_0 where hoce1_0.uuid=$1 | 497 | 2 | 213 |
| select hope1_0.uuid,hope1_0.familyname,hope1_0.givenname,hope1_0.persontype,hope1_0.salutation,hope1_0.title,hope1_0.tradename,hope1_0.version from public.hs_office.person_rv hope1_0 where hope1_0.uuid=$1 | 1015 | 4 | 238 |
| select hore1_0.uuid,hore1_0.anchoruuid,hore1_0.contactuuid,hore1_0.holderuuid,hore1_0.mark,hore1_0.type,hore1_0.version from public.hs_office.relation_rv hore1_0 where hore1_0.uuid=$1 | 517 | 4 | 439 |
| select hoce1_0.uuid,hoce1_0.caption,hoce1_0.emailaddresses,hoce1_0.phonenumbers,hoce1_0.postaladdress,hoce1_0.version from public.hs_office.contact_rv hoce1_0 where hoce1_0.uuid=$1 | 497 | 2 | 213 |
| call rbac.grantRoleToRole(roleUuid, superRoleUuid, superRoleDesc.assumed) | 31316 | 0 | 1 |
| select * from rbac.isGranted(array[granteeId], grantedId) | 44613 | 0 | 0 |
| call buildRbacSystemForHsHostingAsset(NEW) | 2258 | 0 | 7 |
| insert into public.hs_hosting_asset_rv (alarmcontactuuid,assignedtoassetuuid,bookingitemuuid,caption,config,identifier,parentassetuuid,type,version,uuid) values ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10) | 2207 | 0 | 7 |
| insert into hs_hosting_asset (alarmcontactuuid, version, bookingitemuuid, type, parentassetuuid, assignedtoassetuuid, config, uuid, identifier, caption) values (new.alarmcontactuuid, new. version, new. bookingitemuuid, new. type, new. parentassetuuid, new. assignedtoassetuuid, new. config, new. uuid, new. identifier, new. caption) returning * | 2207 | 0 | 7 |
| with recursive grants as ( select descendantUuid, ascendantUuid from RbacGrants where descendantUuid = grantedId union all select ""grant"".descendantUuid, ""grant"".ascendantUuid from RbacGrants ""grant"" inner join grants recur on recur.ascendantUuid = ""grant"".descendantUuid ) select exists ( select $3 from grants where ascendantUuid = any(granteeIds) ) or grantedId = any(granteeIds) | 47538 | 0 | 0 |
insert into public.hs_office_relation_rv (anchoruuid,contactuuid,holderuuid,mark,type,version,uuid) values ($1,$2,$3,$4,$5,$6,$7) | 1261 | 0 | 8 |
| insert into hs_office_relation (uuid, version, anchoruuid, holderuuid, contactuuid, type, mark) values (new.uuid, new. version, new. anchoruuid, new. holderuuid, new. contactuuid, new. type, new. mark) returning * | 1261 | 0 | 8 |
insert into public.hs_office.relation_rv (anchoruuid,contactuuid,holderuuid,mark,type,version,uuid) values ($1,$2,$3,$4,$5,$6,$7) | 1261 | 0 | 8 |
| insert into hs_office.relation (uuid, version, anchoruuid, holderuuid, contactuuid, type, mark) values (new.uuid, new. version, new. anchoruuid, new. holderuuid, new. contactuuid, new. type, new. mark) returning * | 1261 | 0 | 8 |
| call buildRbacSystemForHsOfficeRelation(NEW) | 1276 | 0 | 7 |
| insert into public.hs_booking_item_rv (caption,parentitemuuid,projectuuid,resources,type,validity,version,uuid) values ($1,$2,$3,$4,$5,$6,$7,$8) | 926 | 0 | 7 |
| insert into hs_booking_item (resources, version, projectuuid, type, parentitemuuid, validity, uuid, caption) values (new.resources, new. version, new. projectuuid, new. type, new. parentitemuuid, new. validity, new. uuid, new. caption) returning * | 926 | 0 | 7 |
@ -331,13 +331,13 @@ Now, the longest running queries are these:
| No.| calls | total_m | mean_ms | query |
|---:|---------|--------:|--------:|:-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 1 | 13.093 | 4 | 21 | insert into hs_hosting_asset( uuid, type, bookingitemuuid, parentassetuuid, assignedtoassetuuid, alarmcontactuuid, identifier, caption, config, version) values ( $1, $2, $3, $4, $5, $6, $7, $8, cast($9 as jsonb), $10) |
| 2 | 517 | 4 | 502 | select hore1_0.uuid,hore1_0.anchoruuid,hore1_0.contactuuid,hore1_0.holderuuid,hore1_0.mark,hore1_0.type,hore1_0.version from public.hs_office_relation_rv hore1_0 where hore1_0.uuid=$1 |
| 2 | 517 | 4 | 502 | select hore1_0.uuid,hore1_0.anchoruuid,hore1_0.contactuuid,hore1_0.holderuuid,hore1_0.mark,hore1_0.type,hore1_0.version from public.hs_office.relation_rv hore1_0 where hore1_0.uuid=$1 |
| 3 | 13.144 | 4 | 21 | call buildRbacSystemForHsHostingAsset(NEW) |
| 4 | 96.632 | 3 | 2 | call rbac.grantRoleToRole(roleUuid, superRoleUuid, superRoleDesc.assumed) |
| 5 | 120.815 | 3 | 2 | select * from rbac.isGranted(array[granteeId], grantedId) |
| 6 | 123.740 | 3 | 2 | with recursive grants as ( select descendantUuid, ascendantUuid from RbacGrants where descendantUuid = grantedId union all select "grant".descendantUuid, "grant".ascendantUuid from RbacGrants "grant" inner join grants recur on recur.ascendantUuid = "grant".descendantUuid ) select exists ( select $3 from grants where ascendantUuid = any(granteeIds) ) or grantedId = any(granteeIds) |
| 7 | 497 | 2 | 259 | select hoce1_0.uuid,hoce1_0.caption,hoce1_0.emailaddresses,hoce1_0.phonenumbers,hoce1_0.postaladdress,hoce1_0.version from public.hs_office_contact_rv hoce1_0 where hoce1_0.uuid=$1 |
| 8 | 497 | 2 | 255 | select hope1_0.uuid,hope1_0.familyname,hope1_0.givenname,hope1_0.persontype,hope1_0.salutation,hope1_0.title,hope1_0.tradename,hope1_0.version from public.hs_office_person_rv hope1_0 where hope1_0.uuid=$1 |
| 7 | 497 | 2 | 259 | select hoce1_0.uuid,hoce1_0.caption,hoce1_0.emailaddresses,hoce1_0.phonenumbers,hoce1_0.postaladdress,hoce1_0.version from public.hs_office.contact_rv hoce1_0 where hoce1_0.uuid=$1 |
| 8 | 497 | 2 | 255 | select hope1_0.uuid,hope1_0.familyname,hope1_0.givenname,hope1_0.persontype,hope1_0.salutation,hope1_0.title,hope1_0.tradename,hope1_0.version from public.hs_office.person_rv hope1_0 where hope1_0.uuid=$1 |
| 9 | 13.144 | 1 | 8 | SELECT createRoleWithGrants( hsHostingAssetTENANT(NEW), permissions => array[$7], incomingSuperRoles => array[ hsHostingAssetAGENT(NEW), hsOfficeContactADMIN(newAlarmContact)], outgoingSubRoles => array[ hsBookingItemTENANT(newBookingItem), hsHostingAssetTENANT(newParentAsset)] ) |
| 10 | 13.144 | 1 | 5 | SELECT createRoleWithGrants( hsHostingAssetADMIN(NEW), permissions => array[$7], incomingSuperRoles => array[ hsBookingItemAGENT(newBookingItem), hsHostingAssetAGENT(newParentAsset), hsHostingAssetOWNER(NEW)] ) |
@ -345,7 +345,7 @@ That the `INSERT into hs_hosting_asset` (No. 1) takes up the most time, seems to
It seems that the trigger effects (eg. No. 3 and No. 4) are included in the measure for the causing INSERT, otherwise summing up the totals would exceed the actual total time of the whole import. And it was to be expected that building the RBAC rules for new business objects takes most of the time.
In production, the `SELECT ... FROM hs_office_relation_rv` (No. 2) with about 0.5 seconds could still be a problem. But once we apply the improvements from the hosting asset area also to the office area, this should not be a problem for the import anymore.
In production, the `SELECT ... FROM hs_office.relation_rv` (No. 2) with about 0.5 seconds could still be a problem. But once we apply the improvements from the hosting asset area also to the office area, this should not be a problem for the import anymore.
## Further Options To Explore

View File

@ -4,7 +4,7 @@ import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
import lombok.experimental.SuperBuilder;
import net.hostsharing.hsadminng.hs.booking.project.HsBookingProject;
import net.hostsharing.hsadminng.hs.booking.project.HsBookingProjectRbacEntity;
import net.hostsharing.hsadminng.rbac.generator.RbacView;
import net.hostsharing.hsadminng.rbac.generator.RbacView.SQL;
@ -49,7 +49,7 @@ public class HsBookingItemRbacEntity extends HsBookingItem {
.toRole(GLOBAL, ADMIN).grantPermission(INSERT) // TODO.impl: Why is this necessary to insert test data?
.toRole(GLOBAL, ADMIN).grantPermission(DELETE)
.importEntityAlias("project", HsBookingProject.class, usingDefaultCase(),
.importEntityAlias("project", HsBookingProjectRbacEntity.class, usingDefaultCase(),
dependsOnColumn("projectUuid"),
directlyFetchedByDependsOnColumn(),
NULLABLE)

View File

@ -68,11 +68,11 @@ public abstract class HsBookingProject implements Stringifyable, BaseEntity<HsBo
}
public static RbacView rbac() {
return rbacViewFor("project", HsBookingProject.class)
return rbacViewFor("project", HsBookingProjectRbacEntity.class)
.withIdentityView(SQL.query("""
SELECT bookingProject.uuid as uuid, debitorIV.idName || '-' || base.cleanIdentifier(bookingProject.caption) as idName
FROM hs_booking_project bookingProject
JOIN hs_office_debitor_iv debitorIV ON debitorIV.uuid = bookingProject.debitorUuid
JOIN hs_office.debitor_iv debitorIV ON debitorIV.uuid = bookingProject.debitorUuid
"""))
.withRestrictedViewOrderBy(SQL.expression("caption"))
.withUpdatableColumns("version", "caption")
@ -86,8 +86,8 @@ public abstract class HsBookingProject implements Stringifyable, BaseEntity<HsBo
dependsOnColumn("debitorUuid"),
fetchedBySql("""
SELECT ${columns}
FROM hs_office_relation debitorRel
JOIN hs_office_debitor debitor ON debitor.debitorRelUuid = debitorRel.uuid
FROM hs_office.relation debitorRel
JOIN hs_office.debitor debitor ON debitor.debitorRelUuid = debitorRel.uuid
WHERE debitor.uuid = ${REF}.debitorUuid
"""),
NOT_NULL)

View File

@ -44,7 +44,7 @@ public class HsBookingProjectRbacEntity extends HsBookingProject {
.withIdentityView(SQL.query("""
SELECT bookingProject.uuid as uuid, debitorIV.idName || '-' || base.cleanIdentifier(bookingProject.caption) as idName
FROM hs_booking_project bookingProject
JOIN hs_office_debitor_iv debitorIV ON debitorIV.uuid = bookingProject.debitorUuid
JOIN hs_office.debitor_iv debitorIV ON debitorIV.uuid = bookingProject.debitorUuid
"""))
.withRestrictedViewOrderBy(SQL.expression("caption"))
.withUpdatableColumns("version", "caption")
@ -58,8 +58,8 @@ public class HsBookingProjectRbacEntity extends HsBookingProject {
dependsOnColumn("debitorUuid"),
fetchedBySql("""
SELECT ${columns}
FROM hs_office_relation debitorRel
JOIN hs_office_debitor debitor ON debitor.debitorRelUuid = debitorRel.uuid
FROM hs_office.relation debitorRel
JOIN hs_office.debitor debitor ON debitor.debitorRelUuid = debitorRel.uuid
WHERE debitor.uuid = ${REF}.debitorUuid
"""),
NOT_NULL)

View File

@ -4,7 +4,7 @@ import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
import lombok.experimental.SuperBuilder;
import net.hostsharing.hsadminng.hs.booking.item.HsBookingItem;
import net.hostsharing.hsadminng.hs.booking.item.HsBookingItemRbacEntity;
import net.hostsharing.hsadminng.hs.office.contact.HsOfficeContactRbacEntity;
import net.hostsharing.hsadminng.rbac.generator.RbacView;
import net.hostsharing.hsadminng.rbac.generator.RbacView.SQL;
@ -47,7 +47,7 @@ public class HsHostingAssetRbacEntity extends HsHostingAsset {
.withUpdatableColumns("version", "caption", "config", "assignedToAssetUuid", "alarmContactUuid")
.toRole(GLOBAL, ADMIN).grantPermission(INSERT) // TODO.impl: Why is this necessary to insert test data?
.importEntityAlias("bookingItem", HsBookingItem.class, usingDefaultCase(),
.importEntityAlias("bookingItem", HsBookingItemRbacEntity.class, usingDefaultCase(),
dependsOnColumn("bookingItemUuid"),
directlyFetchedByDependsOnColumn(),
NULLABLE)

View File

@ -19,7 +19,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.Role.*;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_bankaccount_rv")
@Table(schema = "hs_office", name = "bankaccount_rv")
@Getter
@Setter
@Builder

View File

@ -16,7 +16,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.Role.*;
import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
@Entity
@Table(name = "hs_office_contact_rv")
@Table(schema = "hs_office", name = "contact_rv")
@Getter
@Setter
@NoArgsConstructor

View File

@ -10,7 +10,7 @@ import jakarta.persistence.Entity;
import jakarta.persistence.Table;
@Entity
@Table(name = "hs_office_contact")
@Table(schema = "hs_office", name = "contact")
@Getter
@Setter
@NoArgsConstructor

View File

@ -34,7 +34,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_coopassetstransaction_rv")
@Table(schema = "hs_office", name = "coopassetstransaction_rv")
@Getter
@Setter
@Builder

View File

@ -32,7 +32,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_coopsharestransaction_rv")
@Table(schema = "hs_office", name = "coopsharestransaction_rv")
@Getter
@Setter
@Builder

View File

@ -54,7 +54,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_debitor_rv")
@Table(schema = "hs_office", name = "debitor_rv")
@Getter
@Setter
@Builder(toBuilder = true)
@ -87,10 +87,10 @@ public class HsOfficeDebitorEntity implements BaseEntity<HsOfficeDebitorEntity>,
value = """
(
SELECT DISTINCT partner.uuid
FROM hs_office_partner_rv partner
JOIN hs_office_relation_rv dRel
FROM hs_office.partner_rv partner
JOIN hs_office.relation_rv dRel
ON dRel.uuid = debitorreluuid AND dRel.type = 'DEBITOR'
JOIN hs_office_relation_rv pRel
JOIN hs_office.relation_rv pRel
ON pRel.uuid = partner.partnerRelUuid AND pRel.type = 'PARTNER'
WHERE pRel.holderUuid = dRel.anchorUuid
)
@ -170,14 +170,14 @@ public class HsOfficeDebitorEntity implements BaseEntity<HsOfficeDebitorEntity>,
.withIdentityView(SQL.query("""
SELECT debitor.uuid AS uuid,
'D-' || (SELECT partner.partnerNumber
FROM hs_office_partner partner
JOIN hs_office_relation partnerRel
FROM hs_office.partner partner
JOIN hs_office.relation partnerRel
ON partnerRel.uuid = partner.partnerRelUUid AND partnerRel.type = 'PARTNER'
JOIN hs_office_relation debitorRel
JOIN hs_office.relation debitorRel
ON debitorRel.anchorUuid = partnerRel.holderUuid AND debitorRel.type = 'DEBITOR'
WHERE debitorRel.uuid = debitor.debitorRelUuid)
|| debitorNumberSuffix as idName
FROM hs_office_debitor AS debitor
FROM hs_office.debitor AS debitor
"""))
.withRestrictedViewOrderBy(SQL.projection("defaultPrefix"))
.withUpdatableColumns(
@ -209,8 +209,8 @@ public class HsOfficeDebitorEntity implements BaseEntity<HsOfficeDebitorEntity>,
dependsOnColumn("debitorRelUuid"),
fetchedBySql("""
SELECT ${columns}
FROM hs_office_relation AS partnerRel
JOIN hs_office_relation AS debitorRel
FROM hs_office.relation AS partnerRel
JOIN hs_office.relation AS debitorRel
ON debitorRel.type = 'DEBITOR' AND debitorRel.anchorUuid = partnerRel.holderUuid
WHERE partnerRel.type = 'PARTNER'
AND ${REF}.debitorRelUuid = debitorRel.uuid

View File

@ -56,7 +56,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_membership_rv")
@Table(schema = "hs_office", name = "membership_rv")
@Getter
@Setter
@Builder
@ -160,8 +160,8 @@ public class HsOfficeMembershipEntity implements BaseEntity<HsOfficeMembershipEn
.withIdentityView(SQL.query("""
SELECT m.uuid AS uuid,
'M-' || p.partnerNumber || m.memberNumberSuffix as idName
FROM hs_office_membership AS m
JOIN hs_office_partner AS p ON p.uuid = m.partnerUuid
FROM hs_office.membership AS m
JOIN hs_office.partner AS p ON p.uuid = m.partnerUuid
"""))
.withRestrictedViewOrderBy(SQL.projection("validity"))
.withUpdatableColumns("validity", "membershipFeeBillable", "status")
@ -170,8 +170,8 @@ public class HsOfficeMembershipEntity implements BaseEntity<HsOfficeMembershipEn
dependsOnColumn("partnerUuid"),
fetchedBySql("""
SELECT ${columns}
FROM hs_office_partner AS partner
JOIN hs_office_relation AS partnerRel ON partnerRel.uuid = partner.partnerRelUuid
FROM hs_office.partner AS partner
JOIN hs_office.relation AS partnerRel ON partnerRel.uuid = partner.partnerRelUuid
WHERE partner.uuid = ${REF}.partnerUuid
"""),
NOT_NULL)

View File

@ -20,7 +20,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_partner_details_rv")
@Table(schema = "hs_office", name = "partner_details_rv")
@Getter
@Setter
@Builder
@ -71,9 +71,9 @@ public class HsOfficePartnerDetailsEntity implements BaseEntity<HsOfficePartnerD
return rbacViewFor("partnerDetails", HsOfficePartnerDetailsEntity.class)
.withIdentityView(SQL.query("""
SELECT partnerDetails.uuid as uuid, partner_iv.idName as idName
FROM hs_office_partner_details AS partnerDetails
JOIN hs_office_partner partner ON partner.detailsUuid = partnerDetails.uuid
JOIN hs_office_partner_iv partner_iv ON partner_iv.uuid = partner.uuid
FROM hs_office.partner_details AS partnerDetails
JOIN hs_office.partner partner ON partner.detailsUuid = partnerDetails.uuid
JOIN hs_office.partner_iv partner_iv ON partner_iv.uuid = partner.uuid
"""))
.withRestrictedViewOrderBy(SQL.expression("uuid"))
.withUpdatableColumns(

View File

@ -36,7 +36,7 @@ import static java.util.Optional.ofNullable;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_partner_rv")
@Table(schema = "hs_office", name = "partner_rv")
@Getter
@Setter
@Builder

View File

@ -22,7 +22,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_person_rv")
@Table(schema = "hs_office", name = "person_rv")
@Getter
@Setter
@Builder

View File

@ -34,7 +34,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.SQL.directlyFetc
import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
@Entity
@Table(name = "hs_office_relation_rv")
@Table(schema = "hs_office", name = "relation_rv")
@NoArgsConstructor
@Getter
@Setter
@ -45,12 +45,12 @@ public class HsOfficeRelationRbacEntity extends HsOfficeRelation {
public static RbacView rbac() {
return rbacViewFor("relation", HsOfficeRelationRbacEntity.class)
.withIdentityView(SQL.projection("""
(select idName from hs_office_person_iv p where p.uuid = anchorUuid)
(select idName from hs_office.person_iv p where p.uuid = anchorUuid)
|| '-with-' || target.type || '-'
|| (select idName from hs_office_person_iv p where p.uuid = holderUuid)
|| (select idName from hs_office.person_iv p where p.uuid = holderUuid)
"""))
.withRestrictedViewOrderBy(SQL.expression(
"(select idName from hs_office_person_iv p where p.uuid = target.holderUuid)"))
"(select idName from hs_office.person_iv p where p.uuid = target.holderUuid)"))
.withUpdatableColumns("contactUuid")
.importEntityAlias("anchorPerson", HsOfficePersonEntity.class, usingDefaultCase(),
dependsOnColumn("anchorUuid"),

View File

@ -17,13 +17,13 @@ public interface HsOfficeRelationRbacRepository extends Repository<HsOfficeRelat
}
@Query(value = """
SELECT p.* FROM hs_office_relation_rv AS p
SELECT p.* FROM hs_office.relation_rv AS p
WHERE p.anchorUuid = :personUuid OR p.holderUuid = :personUuid
""", nativeQuery = true)
List<HsOfficeRelationRbacEntity> findRelationRelatedToPersonUuid(@NotNull UUID personUuid);
@Query(value = """
SELECT p.* FROM hs_office_relation_rv AS p
SELECT p.* FROM hs_office.relation_rv AS p
WHERE (:relationType IS NULL OR p.type = cast(:relationType AS HsOfficeRelationType))
AND ( p.anchorUuid = :personUuid OR p.holderUuid = :personUuid)
""", nativeQuery = true)

View File

@ -11,7 +11,7 @@ import jakarta.persistence.Table;
@Entity
@Table(name = "hs_office_relation")
@Table(schema = "hs_office", name = "relation")
@NoArgsConstructor
@Getter
@Setter

View File

@ -17,13 +17,13 @@ public interface HsOfficeRelationRealRepository extends Repository<HsOfficeRelat
}
@Query(value = """
SELECT p.* FROM hs_office_relation AS p
SELECT p.* FROM hs_office.relation AS p
WHERE p.anchorUuid = :personUuid OR p.holderUuid = :personUuid
""", nativeQuery = true)
List<HsOfficeRelationRealEntity> findRelationRelatedToPersonUuid(@NotNull UUID personUuid);
@Query(value = """
SELECT p.* FROM hs_office_relation AS p
SELECT p.* FROM hs_office.relation AS p
WHERE (:relationType IS NULL OR p.type = cast(:relationType AS HsOfficeRelationType))
AND ( p.anchorUuid = :personUuid OR p.holderUuid = :personUuid)
""", nativeQuery = true)

View File

@ -33,7 +33,7 @@ import static net.hostsharing.hsadminng.rbac.generator.RbacView.rbacViewFor;
import static net.hostsharing.hsadminng.stringify.Stringify.stringify;
@Entity
@Table(name = "hs_office_sepamandate_rv")
@Table(schema = "hs_office", name = "sepamandate_rv")
@Getter
@Setter
@Builder
@ -104,8 +104,8 @@ public class HsOfficeSepaMandateEntity implements Stringifyable, BaseEntity<HsOf
return rbacViewFor("sepaMandate", HsOfficeSepaMandateEntity.class)
.withIdentityView(query("""
select sm.uuid as uuid, ba.iban || '-' || sm.validity as idName
from hs_office_sepamandate sm
join hs_office_bankaccount ba on ba.uuid = sm.bankAccountUuid
from hs_office.sepamandate sm
join hs_office.bankaccount ba on ba.uuid = sm.bankAccountUuid
"""))
.withRestrictedViewOrderBy(expression("validity"))
.withUpdatableColumns("reference", "agreement", "validity")
@ -114,8 +114,8 @@ public class HsOfficeSepaMandateEntity implements Stringifyable, BaseEntity<HsOf
dependsOnColumn("debitorUuid"),
fetchedBySql("""
SELECT ${columns}
FROM hs_office_relation debitorRel
JOIN hs_office_debitor debitor ON debitor.debitorRelUuid = debitorRel.uuid
FROM hs_office.relation debitorRel
JOIN hs_office.debitor debitor ON debitor.debitorRelUuid = debitorRel.uuid
WHERE debitor.uuid = ${REF}.debitorUuid
"""),
NOT_NULL)

View File

@ -213,7 +213,7 @@ public class InsertTriggerGenerator {
if (g.getSuperRoleDef().isGlobal(GUEST)) {
plPgSql.writeLn(
"""
-- check INSERT INSERT permission for rbac.global anyone
-- check INSERT permission for rbac.global anyone
if ${caseCondition}true then
return NEW;
end if;
@ -222,7 +222,7 @@ public class InsertTriggerGenerator {
} else if (g.getSuperRoleDef().isGlobal(ADMIN)) {
plPgSql.writeLn(
"""
-- check INSERT INSERT if rbac.global ADMIN
-- check INSERT permission if rbac.global ADMIN
if ${caseCondition}rbac.isGlobalAdmin() then
return NEW;
end if;

View File

@ -12,7 +12,6 @@ import jakarta.persistence.Version;
import jakarta.validation.constraints.NotNull;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.nio.file.Path;
import java.util.*;
import java.util.function.Consumer;
@ -983,10 +982,10 @@ public class RbacView {
String getRawTableShortName() {
// TODO.impl: some combined function and trigger names are too long
// maybe we should shorten the table name e.g. hs_office_coopsharestransaction -> hsof.coopsharetx
// maybe we should shorten the table name e.g. hs_office.coopsharestransaction -> hsof.coopsharetx
// this is just a workaround:
return getRawTableName()
.replace("hs_office_", "hsof_")
.replace("hs_office.", "hsof.")
.replace("hs_booking_", "hsbk_")
.replace("hs_hosting_", "hsho_")
.replace("coopsharestransaction", "coopsharetx")
@ -1274,13 +1273,14 @@ public class RbacView {
public static Set<Class<? extends BaseEntity>> findRbacEntityClasses(String packageName) {
final var reflections = new Reflections(packageName, TypeAnnotationsScanner.class);
return reflections.getTypesAnnotatedWith(Entity.class).stream()
.filter(c -> stream(c.getInterfaces()).anyMatch(i -> i== BaseEntity.class))
final Set<Class<? extends BaseEntity>> rbacEntityClasses = reflections.getTypesAnnotatedWith(Entity.class).stream()
.filter(BaseEntity.class::isAssignableFrom)
.filter(c -> stream(c.getDeclaredMethods())
.anyMatch(m -> m.getName().equals("rbac") && Modifier.isStatic(m.getModifiers()))
.anyMatch(m -> m.getName().equals("rbac") && isStatic(m.getModifiers()))
)
.map(RbacView::castToSubclassOfBaseEntity)
.collect(Collectors.toSet());
return rbacEntityClasses;
}
@SuppressWarnings("unchecked")

View File

@ -29,7 +29,7 @@ class RolesGrantsAndPermissionsGenerator {
private final String liquibaseTagPrefix;
private final String simpleEntityName;
private final String simpleEntityVarName;
private final String rawTableName;
private final String qualifiedRawTableName;
RolesGrantsAndPermissionsGenerator(final RbacView rbacDef, final String liquibaseTagPrefix) {
this.rbacDef = rbacDef;
@ -40,7 +40,7 @@ class RolesGrantsAndPermissionsGenerator {
simpleEntityVarName = rbacDef.getRootEntityAlias().simpleName();
simpleEntityName = capitalize(simpleEntityVarName);
rawTableName = rbacDef.getRootEntityAlias().getRawTableNameWithSchema();
qualifiedRawTableName = rbacDef.getRootEntityAlias().getRawTableNameWithSchema();
}
void generateTo(final StringWriter plPgSql) {
@ -66,13 +66,12 @@ class RolesGrantsAndPermissionsGenerator {
Creates the roles, grants and permission for the AFTER INSERT TRIGGER.
*/
create or replace procedure buildRbacSystemFor${simpleEntityName}(
NEW ${rawTableName}
create or replace procedure ${rawTableQualifiedName}_build_rbac_system(
NEW ${rawTableQualifiedName}
)
language plpgsql as $$
"""
.replace("${simpleEntityName}", simpleEntityName)
.replace("${rawTableName}", rawTableName));
.replace("${rawTableQualifiedName}", qualifiedRawTableName));
plPgSql.writeLn("declare");
plPgSql.indented(() -> {
@ -106,21 +105,21 @@ class RolesGrantsAndPermissionsGenerator {
Called from the AFTER UPDATE TRIGGER to re-wire the grants.
*/
create or replace procedure updateRbacRulesFor${simpleEntityName}(
OLD ${rawTableName},
NEW ${rawTableName}
create or replace procedure ${rawTableQualifiedName}_update_rbac_system(
OLD ${rawTableQualifiedName},
NEW ${rawTableQualifiedName}
)
language plpgsql as $$
begin
if ${updateConditions} then
delete from rbac.grants g where g.grantedbytriggerof = OLD.uuid;
call buildRbacSystemFor${simpleEntityName}(NEW);
call ${rawTableQualifiedName}_build_rbac_system(NEW);
end if;
end; $$;
""",
with("simpleEntityName", simpleEntityName),
with("rawTableName", rawTableName),
with("rawTableQualifiedName", qualifiedRawTableName),
with("updateConditions", updateConditions));
}
@ -130,16 +129,15 @@ class RolesGrantsAndPermissionsGenerator {
Called from the AFTER UPDATE TRIGGER to re-wire the grants.
*/
create or replace procedure updateRbacRulesFor${simpleEntityName}(
OLD ${rawTableName},
NEW ${rawTableName}
create or replace procedure ${rawTableQualifiedName}_update_rbac_system(
OLD ${rawTableQualifiedName},
NEW ${rawTableQualifiedName}
)
language plpgsql as $$
declare
"""
.replace("${simpleEntityName}", simpleEntityName)
.replace("${rawTableName}", rawTableName));
""",
with("rawTableQualifiedName", qualifiedRawTableName));
plPgSql.chopEmptyLines();
plPgSql.indented(() -> {
@ -514,25 +512,25 @@ class RolesGrantsAndPermissionsGenerator {
plPgSql.writeLn("""
/*
AFTER INSERT TRIGGER to create the role+grant structure for a new ${rawTableName} row.
AFTER INSERT TRIGGER to create the role+grant structure for a new ${rawTableQualifiedName} row.
*/
create or replace function insertTriggerFor${simpleEntityName}_tf()
create or replace function ${rawTableQualifiedName}_build_rbac_system_after_insert_tf()
returns trigger
language plpgsql
strict as $$
begin
call buildRbacSystemFor${simpleEntityName}(NEW);
call ${rawTableQualifiedName}_build_rbac_system(NEW);
return NEW;
end; $$;
create trigger insertTriggerFor${simpleEntityName}_tg
after insert on ${rawTableName}
create trigger build_rbac_system_after_insert_tg
after insert on ${rawTableQualifiedName}
for each row
execute procedure insertTriggerFor${simpleEntityName}_tf();
execute procedure ${rawTableQualifiedName}_build_rbac_system_after_insert_tf();
"""
.replace("${simpleEntityName}", simpleEntityName)
.replace("${rawTableName}", rawTableName)
.replace("${schemaPrefix}", schemaPrefix(qualifiedRawTableName))
.replace("${rawTableQualifiedName}", qualifiedRawTableName)
);
generateFooter(plPgSql);
@ -549,30 +547,35 @@ class RolesGrantsAndPermissionsGenerator {
plPgSql.writeLn("""
/*
AFTER INSERT TRIGGER to re-wire the grant structure for a new ${rawTableName} row.
AFTER UPDATE TRIGGER to re-wire the grant structure for a new ${rawTableQualifiedName} row.
*/
create or replace function updateTriggerFor${simpleEntityName}_tf()
create or replace function ${rawTableQualifiedName}_update_rbac_system_after_update_tf()
returns trigger
language plpgsql
strict as $$
begin
call updateRbacRulesFor${simpleEntityName}(OLD, NEW);
call ${rawTableQualifiedName}_update_rbac_system(OLD, NEW);
return NEW;
end; $$;
create trigger updateTriggerFor${simpleEntityName}_tg
after update on ${rawTableName}
create trigger update_rbac_system_after_update_tg
after update on ${rawTableQualifiedName}
for each row
execute procedure updateTriggerFor${simpleEntityName}_tf();
execute procedure ${rawTableQualifiedName}_update_rbac_system_after_update_tf();
"""
.replace("${simpleEntityName}", simpleEntityName)
.replace("${rawTableName}", rawTableName)
.replace("${rawTableQualifiedName}", qualifiedRawTableName)
);
generateFooter(plPgSql);
}
private String schemaPrefix(final String qualifiedIdentifier) {
return qualifiedIdentifier.contains(".")
? qualifiedIdentifier.split("\\.")[0] + "."
: "";
}
private static void generateFooter(final StringWriter plPgSql) {
plPgSql.writeLn("--//");
plPgSql.writeLn();

View File

@ -384,7 +384,7 @@ create index on rbac.permission (objectUuid, op);
create index on rbac.permission (opTableName, op);
ALTER TABLE rbac.permission
ADD CONSTRAINT RbacPermission_uc UNIQUE NULLS NOT DISTINCT (objectUuid, op, opTableName);
ADD CONSTRAINT unique_including_null_values UNIQUE NULLS NOT DISTINCT (objectUuid, op, opTableName);
call base.create_journal('rbac.permission');

View File

@ -24,7 +24,7 @@ call rbac.generateRbacRoleDescriptors('testCustomer', 'rbactest.customer');
Creates the roles, grants and permission for the AFTER INSERT TRIGGER.
*/
create or replace procedure buildRbacSystemForTestCustomer(
create or replace procedure rbactest.customer_build_rbac_system(
NEW rbactest.customer
)
language plpgsql as $$
@ -60,19 +60,19 @@ end; $$;
AFTER INSERT TRIGGER to create the role+grant structure for a new rbactest.customer row.
*/
create or replace function insertTriggerForTestCustomer_tf()
create or replace function rbactest.customer_build_rbac_system_after_insert_tf()
returns trigger
language plpgsql
strict as $$
begin
call buildRbacSystemForTestCustomer(NEW);
call rbactest.customer_build_rbac_system(NEW);
return NEW;
end; $$;
create trigger insertTriggerForTestCustomer_tg
create trigger build_rbac_system_after_insert_tg
after insert on rbactest.customer
for each row
execute procedure insertTriggerForTestCustomer_tf();
execute procedure rbactest.customer_build_rbac_system_after_insert_tf();
--//
@ -137,7 +137,7 @@ create or replace function rbactest.customer_insert_permission_check_tf()
declare
superObjectUuid uuid;
begin
-- check INSERT INSERT if rbac.global ADMIN
-- check INSERT permission if rbac.global ADMIN
if rbac.isGlobalAdmin() then
return NEW;
end if;

View File

@ -24,7 +24,7 @@ call rbac.generateRbacRoleDescriptors('testPackage', 'rbactest.package');
Creates the roles, grants and permission for the AFTER INSERT TRIGGER.
*/
create or replace procedure buildRbacSystemForTestPackage(
create or replace procedure rbactest.package_build_rbac_system(
NEW rbactest.package
)
language plpgsql as $$
@ -64,19 +64,19 @@ end; $$;
AFTER INSERT TRIGGER to create the role+grant structure for a new rbactest.package row.
*/
create or replace function insertTriggerForTestPackage_tf()
create or replace function rbactest.package_build_rbac_system_after_insert_tf()
returns trigger
language plpgsql
strict as $$
begin
call buildRbacSystemForTestPackage(NEW);
call rbactest.package_build_rbac_system(NEW);
return NEW;
end; $$;
create trigger insertTriggerForTestPackage_tg
create trigger build_rbac_system_after_insert_tg
after insert on rbactest.package
for each row
execute procedure insertTriggerForTestPackage_tf();
execute procedure rbactest.package_build_rbac_system_after_insert_tf();
--//
@ -88,7 +88,7 @@ execute procedure insertTriggerForTestPackage_tf();
Called from the AFTER UPDATE TRIGGER to re-wire the grants.
*/
create or replace procedure updateRbacRulesForTestPackage(
create or replace procedure rbactest.package_update_rbac_system(
OLD rbactest.package,
NEW rbactest.package
)
@ -122,22 +122,22 @@ begin
end; $$;
/*
AFTER INSERT TRIGGER to re-wire the grant structure for a new rbactest.package row.
AFTER UPDATE TRIGGER to re-wire the grant structure for a new rbactest.package row.
*/
create or replace function updateTriggerForTestPackage_tf()
create or replace function rbactest.package_update_rbac_system_after_update_tf()
returns trigger
language plpgsql
strict as $$
begin
call updateRbacRulesForTestPackage(OLD, NEW);
call rbactest.package_update_rbac_system(OLD, NEW);
return NEW;
end; $$;
create trigger updateTriggerForTestPackage_tg
create trigger update_rbac_system_after_update_tg
after update on rbactest.package
for each row
execute procedure updateTriggerForTestPackage_tf();
execute procedure rbactest.package_update_rbac_system_after_update_tf();
--//

View File

@ -24,7 +24,7 @@ call rbac.generateRbacRoleDescriptors('testDomain', 'rbactest.domain');
Creates the roles, grants and permission for the AFTER INSERT TRIGGER.
*/
create or replace procedure buildRbacSystemForTestDomain(
create or replace procedure rbactest.domain_build_rbac_system(
NEW rbactest.domain
)
language plpgsql as $$
@ -60,19 +60,19 @@ end; $$;
AFTER INSERT TRIGGER to create the role+grant structure for a new rbactest.domain row.
*/
create or replace function insertTriggerForTestDomain_tf()
create or replace function rbactest.domain_build_rbac_system_after_insert_tf()
returns trigger
language plpgsql
strict as $$
begin
call buildRbacSystemForTestDomain(NEW);
call rbactest.domain_build_rbac_system(NEW);
return NEW;
end; $$;
create trigger insertTriggerForTestDomain_tg
create trigger build_rbac_system_after_insert_tg
after insert on rbactest.domain
for each row
execute procedure insertTriggerForTestDomain_tf();
execute procedure rbactest.domain_build_rbac_system_after_insert_tf();
--//
@ -84,7 +84,7 @@ execute procedure insertTriggerForTestDomain_tf();
Called from the AFTER UPDATE TRIGGER to re-wire the grants.
*/
create or replace procedure updateRbacRulesForTestDomain(
create or replace procedure rbactest.domain_update_rbac_system(
OLD rbactest.domain,
NEW rbactest.domain
)
@ -121,22 +121,22 @@ begin
end; $$;
/*
AFTER INSERT TRIGGER to re-wire the grant structure for a new rbactest.domain row.
AFTER UPDATE TRIGGER to re-wire the grant structure for a new rbactest.domain row.
*/
create or replace function updateTriggerForTestDomain_tf()
create or replace function rbactest.domain_update_rbac_system_after_update_tf()
returns trigger
language plpgsql
strict as $$
begin
call updateRbacRulesForTestDomain(OLD, NEW);
call rbactest.domain_update_rbac_system(OLD, NEW);
return NEW;
end; $$;
create trigger updateTriggerForTestDomain_tg
create trigger update_rbac_system_after_update_tg
after update on rbactest.domain
for each row
execute procedure updateTriggerForTestDomain_tf();
execute procedure rbactest.domain_update_rbac_system_after_update_tf();
--//

View File

@ -0,0 +1,8 @@
--liquibase formatted sql
-- ============================================================================
--changeset michael.hoennig:hs-office-SCHEMA endDelimiter:--//
-- ----------------------------------------------------------------------------
CREATE SCHEMA hs_office;
--//

View File

@ -4,7 +4,7 @@
--changeset michael.hoennig:hs-office-contact-MAIN-TABLE endDelimiter:--//
-- ----------------------------------------------------------------------------
create table if not exists hs_office_contact
create table if not exists hs_office.contact
(
uuid uuid unique references rbac.object (uuid) initially deferred,
version int not null default 0,
@ -20,5 +20,5 @@ create table if not exists hs_office_contact
--changeset michael.hoennig:hs-office-contact-MAIN-TABLE-JOURNAL endDelimiter:--//
-- ----------------------------------------------------------------------------
call base.create_journal('hs_office_contact');
call base.create_journal('hs_office.contact');
--//

View File

@ -3,29 +3,29 @@
-- ============================================================================
--changeset michael.hoennig:hs-office-contact-rbac-OBJECT endDelimiter:--//
--changeset RbacObjectGenerator:hs-office-contact-rbac-OBJECT endDelimiter:--//
-- ----------------------------------------------------------------------------
call rbac.generateRelatedRbacObject('hs_office_contact');
call rbac.generateRelatedRbacObject('hs_office.contact');
--//
-- ============================================================================
--changeset michael.hoennig:hs-office-contact-rbac-ROLE-DESCRIPTORS endDelimiter:--//
--changeset RbacRoleDescriptorsGenerator:hs-office-contact-rbac-ROLE-DESCRIPTORS endDelimiter:--//
-- ----------------------------------------------------------------------------
call rbac.generateRbacRoleDescriptors('hsOfficeContact', 'hs_office_contact');
call rbac.generateRbacRoleDescriptors('hsOfficeContact', 'hs_office.contact');
--//
-- ============================================================================
--changeset michael.hoennig:hs-office-contact-rbac-insert-trigger endDelimiter:--//
--changeset RolesGrantsAndPermissionsGenerator:hs-office-contact-rbac-insert-trigger endDelimiter:--//
-- ----------------------------------------------------------------------------
/*
Creates the roles, grants and permission for the AFTER INSERT TRIGGER.
*/
create or replace procedure buildRbacSystemForHsOfficeContact(
NEW hs_office_contact
create or replace procedure hs_office.contact_build_rbac_system(
NEW hs_office.contact
)
language plpgsql as $$
@ -37,7 +37,7 @@ begin
perform rbac.defineRoleWithGrants(
hsOfficeContactOWNER(NEW),
permissions => array['DELETE'],
incomingSuperRoles => array[rbac.globalAdmin()],
incomingSuperRoles => array[rbac.globalADMIN()],
subjectUuids => array[rbac.currentSubjectUuid()]
);
@ -57,30 +57,30 @@ begin
end; $$;
/*
AFTER INSERT TRIGGER to create the role+grant structure for a new hs_office_contact row.
AFTER INSERT TRIGGER to create the role+grant structure for a new hs_office.contact row.
*/
create or replace function insertTriggerForHsOfficeContact_tf()
create or replace function hs_office.contact_build_rbac_system_after_insert_tf()
returns trigger
language plpgsql
strict as $$
begin
call buildRbacSystemForHsOfficeContact(NEW);
call hs_office.contact_build_rbac_system(NEW);
return NEW;
end; $$;
create trigger insertTriggerForHsOfficeContact_tg
after insert on hs_office_contact
create trigger build_rbac_system_after_insert_tg
after insert on hs_office.contact
for each row
execute procedure insertTriggerForHsOfficeContact_tf();
execute procedure hs_office.contact_build_rbac_system_after_insert_tf();
--//
-- ============================================================================
--changeset michael.hoennig:hs-office-contact-rbac-IDENTITY-VIEW endDelimiter:--//
--changeset RbacIdentityViewGenerator:hs-office-contact-rbac-IDENTITY-VIEW endDelimiter:--//
-- ----------------------------------------------------------------------------
call rbac.generateRbacIdentityViewFromProjection('hs_office_contact',
call rbac.generateRbacIdentityViewFromProjection('hs_office.contact',
$idName$
caption
$idName$);
@ -88,9 +88,9 @@ call rbac.generateRbacIdentityViewFromProjection('hs_office_contact',
-- ============================================================================
--changeset michael.hoennig:hs-office-contact-rbac-RESTRICTED-VIEW endDelimiter:--//
--changeset RbacRestrictedViewGenerator:hs-office-contact-rbac-RESTRICTED-VIEW endDelimiter:--//
-- ----------------------------------------------------------------------------
call rbac.generateRbacRestrictedView('hs_office_contact',
call rbac.generateRbacRestrictedView('hs_office.contact',
$orderBy$
caption
$orderBy$,