Add Auto Incrementing Primary Keys to tables with no PKs#13844
Add Auto Incrementing Primary Keys to tables with no PKs#13844dakshina99 wants to merge 1 commit into
Conversation
📝 WalkthroughWalkthroughNine SQL dialect files are updated to add auto-generated integer ChangesSchema Normalization: Surrogate Key Migration
Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes Suggested reviewers
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Pull request overview
This PR updates the API-M database initialization SQL scripts to introduce a surrogate, auto-incrementing integer primary key (ID) for several tables that previously lacked a simple PK, with Oracle-specific sequence/trigger support to emulate auto-increment behavior.
Changes:
- Added
IDauto-increment (or sequence/trigger) +PRIMARY KEY (ID)to:IDN_OAUTH2_TOKEN_BINDING,AM_SCOPE_BINDING,AM_API_REVISION_METADATA,AM_WEBHOOKS_UNSUBSCRIPTIONacross multiple RDBMS scripts. - Added PostgreSQL sequences for the new
IDdefaults. - Added Oracle/Oracle RAC/Oracle 23c sequences + triggers to populate the new
IDcolumns.
Reviewed changes
Copilot reviewed 9 out of 9 changed files in this pull request and generated 2 comments.
Show a summary per file
| File | Description |
|---|---|
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/postgresql.sql | Adds sequences and ID PKs for the affected tables in PostgreSQL. |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql | Adds ID PKs plus sequences/triggers for auto-increment behavior in Oracle. |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_rac.sql | Mirrors Oracle changes for RAC variant with sequences/triggers. |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql | Mirrors Oracle changes for Oracle 23c variant with sequences/triggers. |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql.sql | Adds AUTO_INCREMENT ID PKs for the affected tables in MySQL. |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql | Adds AUTO_INCREMENT ID PKs for several tables in MySQL NDB cluster script (but currently incomplete for IDN_OAUTH2_TOKEN_BINDING). |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mssql.sql | Adds IDENTITY ID PKs for the affected tables in SQL Server. |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/h2.sql | Adds AUTO_INCREMENT ID PKs for the affected tables in H2. |
| features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/db2.sql | Adds IDENTITY ID PKs for the affected tables in DB2. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| ID INTEGER NOT NULL AUTO_INCREMENT, | ||
| SCOPE_ID INTEGER NOT NULL, | ||
| SCOPE_BINDING VARCHAR(255) NOT NULL, | ||
| BINDING_TYPE VARCHAR(255) NOT NULL, | ||
| PRIMARY KEY (ID), |
| DROP TABLE IF EXISTS IDN_OAUTH2_TOKEN_BINDING; | ||
| DROP SEQUENCE IF EXISTS IDN_OAUTH2_TOKEN_BINDING_PK_SEQ; | ||
| CREATE SEQUENCE IDN_OAUTH2_TOKEN_BINDING_PK_SEQ; | ||
| CREATE TABLE IDN_OAUTH2_TOKEN_BINDING ( | ||
| ID INTEGER DEFAULT NEXTVAL('IDN_OAUTH2_TOKEN_BINDING_PK_SEQ') NOT NULL, |
There was a problem hiding this comment.
Actionable comments posted: 15
🧹 Nitpick comments (2)
features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql (1)
3824-3835: 💤 Low valueConsider adding UNIQUE constraint if duplicate prevention is required.
If the previous composite primary key was on columns like
(API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC), switching to a surrogate ID without a UNIQUE constraint allows duplicate unsubscription records. If this table is intended as an append-only log where duplicates are acceptable, this is fine. Otherwise, consider adding a unique constraint.Please confirm whether duplicate unsubscription records for the same webhook are acceptable, or if a UNIQUE constraint should be added to preserve data integrity.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql` around lines 3824 - 3835, The table AM_WEBHOOKS_UNSUBSCRIPTION was converted to use a surrogate PK (ID) which allows duplicate unsubscription rows; decide whether duplicates are acceptable and if not, add a UNIQUE constraint on the composite columns (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC) to enforce uniqueness. Update the table definition for AM_WEBHOOKS_UNSUBSCRIPTION to include a UNIQUE constraint referencing those columns (or restore the previous composite PK) and ensure any insert logic (if present) handles unique constraint violations appropriately. Be explicit about the constraint name when adding it so it can be referenced/rolled back if needed.features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql (1)
2639-2650: 💤 Low valueVerify if UNIQUE constraint on business columns is intentional.
The
AM_WEBHOOKS_UNSUBSCRIPTIONtable now uses surrogateIDas the primary key but has no UNIQUE constraint on the natural key columns (e.g.,API_UUID,APPLICATION_ID,TENANT_DOMAIN,HUB_CALLBACK_URL,HUB_TOPIC).If the previous schema enforced uniqueness via a composite primary key, that guarantee is now lost. Please verify whether allowing duplicate unsubscription records is acceptable for the business logic. If not, add a UNIQUE constraint on the appropriate columns.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql` around lines 2639 - 2650, The new AM_WEBHOOKS_UNSUBSCRIPTION table uses a surrogate PK (ID) but dropped the previous uniqueness guarantee on the natural key; confirm whether duplicates of (API_UUID, APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL, HUB_TOPIC) are allowed and, if not, add a UNIQUE constraint on those columns (or the correct subset) to restore the business-rule uniqueness for AM_WEBHOOKS_UNSUBSCRIPTION; locate the CREATE TABLE for AM_WEBHOOKS_UNSUBSCRIPTION and add a UNIQUE(...) clause referencing the appropriate columns.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/db2.sql`:
- Around line 3250-3260: The table AM_WEBHOOKS_UNSUBSCRIPTION lost its previous
business-key uniqueness; add a UNIQUE constraint on the prior composite business
key (the columns used to identify an unsubscription) alongside the surrogate ID
to prevent duplicate unsubscriptions — for example, alter the CREATE TABLE for
AM_WEBHOOKS_UNSUBSCRIPTION to include a UNIQUE(...) clause referencing the
previous business-key columns (e.g., API_UUID, APPLICATION_ID, TENANT_DOMAIN,
HUB_TOPIC or the exact composite used previously) so the surrogate PRIMARY
KEY(ID) stays and the old composite uniqueness is preserved.
- Around line 3092-3098: The migration replaced the natural key by making
AM_SCOPE_BINDING PRIMARY KEY (ID) but removed the uniqueness of the previous
natural key; add back a UNIQUE constraint on (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) to prevent duplicate bindings. Modify the AM_SCOPE_BINDING table
definition (the CREATE TABLE for AM_SCOPE_BINDING) to include UNIQUE (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) alongside PRIMARY KEY (ID) so it matches the
uniqueness semantics used by IDN_OAUTH2_SCOPE_BINDING.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/h2.sql`:
- Around line 2467-2477: The new AM_WEBHOOKS_UNSUBSCRIPTION table definition
removed the previous composite business key, allowing duplicate unsubscriptions;
add a UNIQUE constraint on the original composite columns to preserve that
uniqueness (e.g. add UNIQUE (API_UUID, APPLICATION_ID, TENANT_DOMAIN,
HUB_CALLBACK_URL, HUB_TOPIC) in the CREATE TABLE for AM_WEBHOOKS_UNSUBSCRIPTION,
optionally naming the constraint like
UNQ_AM_WEBHOOKS_UNSUBSCRIPTION_BUSINESSKEY) so the combination of those fields
cannot be inserted more than once.
- Around line 2303-2309: The new AM_SCOPE_BINDING table drops the previous
business-key uniqueness by only declaring PRIMARY KEY (ID); add a unique
constraint to preserve the natural/business key by declaring UNIQUE (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) on the table definition so duplicates of that
triple cannot be inserted while keeping ID as the surrogate PK; modify the
CREATE TABLE for AM_SCOPE_BINDING to include this UNIQUE constraint referencing
the existing columns SCOPE_ID, SCOPE_BINDING and BINDING_TYPE.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mssql.sql`:
- Around line 2723-2732: The table AM_WEBHOOKS_UNSUBSCRIPTION was changed to use
PRIMARY KEY (ID) but lost the original business-key uniqueness; add a UNIQUE
constraint on the original unsubscribe key columns to restore idempotency by
declaring UNIQUE (API_UUID, APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL,
HUB_TOPIC) in the CREATE TABLE statement (while leaving PRIMARY KEY (ID) intact)
so duplicate logical unsubscribe records cannot be inserted.
- Around line 2564-2569: The AM_SCOPE_BINDING table lost its business-key
uniqueness when it was changed to PRIMARY KEY (ID), allowing duplicate
(SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) rows; restore data integrity by adding a
UNIQUE constraint or unique index on the triple (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) for the AM_SCOPE_BINDING table (update the SQL in mssql.sql near
the table definition) so that inserts/updates cannot create duplicates while
keeping the surrogate ID primary key.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql`:
- Around line 2493-2500: The AM_SCOPE_BINDING table adds a surrogate primary key
ID but is missing a UNIQUE constraint on the natural key, so add a UNIQUE
constraint on (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) in the AM_SCOPE_BINDING
CREATE TABLE statement to prevent duplicate entries; modify the AM_SCOPE_BINDING
definition (the table with PRIMARY KEY (ID) and FOREIGN KEY (SCOPE_ID)
REFERENCES AM_SCOPE) to include UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE).
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql.sql`:
- Around line 2508-2517: The table AM_WEBHOOKS_UNSUBSCRIPTION currently uses a
surrogate primary key (ID) but lost the previous composite business key; add a
UNIQUE constraint on the former composite columns to prevent duplicate logical
unsubscribe records by declaring UNIQUE(API_UUID, APPLICATION_ID, TENANT_DOMAIN,
HUB_CALLBACK_URL, HUB_TOPIC) in the table definition (alongside PRIMARY KEY
(ID)) so the business key is enforced while keeping the surrogate key.
- Around line 2343-2348: The AM_SCOPE_BINDING table currently only defines ID as
the primary key which allows duplicate natural-key rows; add a UNIQUE constraint
on (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) while keeping ID as the surrogate PK
and the existing FOREIGN KEY on SCOPE_ID. Locate the table definition for
AM_SCOPE_BINDING and add a UNIQUE clause (e.g., UNIQUE (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) with an appropriate constraint name) alongside the PRIMARY KEY and
FOREIGN KEY declarations.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql`:
- Around line 3630-3648: The AM_SCOPE_BINDING table definition is missing a
UNIQUE constraint on the natural key, allowing duplicate bindings; update the
CREATE TABLE for AM_SCOPE_BINDING to include UNIQUE (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) alongside the PRIMARY KEY and FOREIGN KEY so the combination of
SCOPE_ID, SCOPE_BINDING, and BINDING_TYPE is enforced as unique; ensure the
change is applied in the AM_SCOPE_BINDING CREATE TABLE statement (and mirrored
across other dialect files: db2.sql, mssql.sql, oracle.sql, oracle_rac.sql)
while leaving the AM_SCOPE_BINDING_SEQ and AM_SCOPE_BINDING_TRIG unchanged.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_rac.sql`:
- Around line 3576-3586: The table AM_WEBHOOKS_UNSUBSCRIPTION currently uses
only PRIMARY KEY (ID) which removes the previous business-key uniqueness; add
back a UNIQUE constraint on the composite business-key columns (API_UUID,
APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL, HUB_TOPIC) so duplicates cannot
be inserted while keeping the surrogate ID primary key (i.e., keep PRIMARY KEY
(ID) and add UNIQUE(...) on those columns), ensuring the constraint name is
descriptive and consistent with existing naming conventions.
- Around line 3392-3398: The CREATE TABLE for AM_SCOPE_BINDING replaced the
business key with a surrogate PK (ID) but removed uniqueness on the original
tuple; update the DDL to keep ID as PRIMARY KEY and add a UNIQUE constraint on
(SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) so duplicate bindings cannot be
inserted; modify the AM_SCOPE_BINDING definition to include a UNIQUE (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) clause while retaining the FOREIGN KEY on SCOPE_ID
and PRIMARY KEY (ID).
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql`:
- Around line 3617-3624: The AM_SCOPE_BINDING table now uses a surrogate ID but
lacks a UNIQUE constraint on the former natural key, allowing duplicate entries;
update the AM_SCOPE_BINDING DDL to add a UNIQUE constraint on (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) so those three columns remain unique (mirror the
constraint used by IDN_OAUTH2_SCOPE_BINDING), ensuring the UNIQUE is declared
for AM_SCOPE_BINDING alongside the PRIMARY KEY(ID).
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/postgresql.sql`:
- Around line 2829-2839: The CREATE TABLE for AM_WEBHOOKS_UNSUBSCRIPTION
replaced the previous composite business key with a surrogate ID and thus lost
uniqueness; restore the original composite uniqueness by adding a UNIQUE
constraint (or unique index) on the combination of API_UUID, APPLICATION_ID,
TENANT_DOMAIN, HUB_CALLBACK_URL and HUB_TOPIC in the AM_WEBHOOKS_UNSUBSCRIPTION
definition (or immediately after creation) so the table keeps the old
business-key uniqueness while still having the ID primary key.
- Around line 2665-2671: The table AM_SCOPE_BINDING currently only has a
surrogate primary key ID which allows duplicate logical bindings; add a
uniqueness constraint (or unique index) on the tuple (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) to restore the original uniqueness semantics—modify the
AM_SCOPE_BINDING DDL to include a UNIQUE constraint on those three columns (or
create a UNIQUE INDEX on SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) and ensure the
constraint name is descriptive (e.g., AM_SCOPE_BINDING_UQ) so duplicate
(scope_id, scope_binding, binding_type) rows are rejected.
---
Nitpick comments:
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql`:
- Around line 2639-2650: The new AM_WEBHOOKS_UNSUBSCRIPTION table uses a
surrogate PK (ID) but dropped the previous uniqueness guarantee on the natural
key; confirm whether duplicates of (API_UUID, APPLICATION_ID, TENANT_DOMAIN,
HUB_CALLBACK_URL, HUB_TOPIC) are allowed and, if not, add a UNIQUE constraint on
those columns (or the correct subset) to restore the business-rule uniqueness
for AM_WEBHOOKS_UNSUBSCRIPTION; locate the CREATE TABLE for
AM_WEBHOOKS_UNSUBSCRIPTION and add a UNIQUE(...) clause referencing the
appropriate columns.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql`:
- Around line 3824-3835: The table AM_WEBHOOKS_UNSUBSCRIPTION was converted to
use a surrogate PK (ID) which allows duplicate unsubscription rows; decide
whether duplicates are acceptable and if not, add a UNIQUE constraint on the
composite columns (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC) to
enforce uniqueness. Update the table definition for AM_WEBHOOKS_UNSUBSCRIPTION
to include a UNIQUE constraint referencing those columns (or restore the
previous composite PK) and ensure any insert logic (if present) handles unique
constraint violations appropriately. Be explicit about the constraint name when
adding it so it can be referenced/rolled back if needed.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 19cc5d74-0237-45e3-a397-415724b3886d
📒 Files selected for processing (9)
features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/db2.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/h2.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mssql.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_rac.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/postgresql.sql
| CREATE TABLE AM_SCOPE_BINDING ( | ||
| ID INTEGER NOT NULL GENERATED ALWAYS AS IDENTITY (START WITH 1 INCREMENT BY 1), | ||
| SCOPE_ID INTEGER NOT NULL, | ||
| SCOPE_BINDING VARCHAR(255) NOT NULL, | ||
| BINDING_TYPE VARCHAR(255) NOT NULL, | ||
| PRIMARY KEY (ID), | ||
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) |
There was a problem hiding this comment.
Keep the natural key unique after adding ID.
Switching AM_SCOPE_BINDING to PRIMARY KEY (ID) without a replacement UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) now allows duplicate bindings for the same scope. That weakens the old key contract and also makes this table inconsistent with IDN_OAUTH2_SCOPE_BINDING earlier in the same script.
Suggested fix
CREATE TABLE AM_SCOPE_BINDING (
ID INTEGER NOT NULL GENERATED ALWAYS AS IDENTITY (START WITH 1 INCREMENT BY 1),
SCOPE_ID INTEGER NOT NULL,
SCOPE_BINDING VARCHAR(255) NOT NULL,
BINDING_TYPE VARCHAR(255) NOT NULL,
+ UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE),
PRIMARY KEY (ID),
FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE)📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| CREATE TABLE AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL GENERATED ALWAYS AS IDENTITY (START WITH 1 INCREMENT BY 1), | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) | |
| CREATE TABLE AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL GENERATED ALWAYS AS IDENTITY (START WITH 1 INCREMENT BY 1), | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/db2.sql`
around lines 3092 - 3098, The migration replaced the natural key by making
AM_SCOPE_BINDING PRIMARY KEY (ID) but removed the uniqueness of the previous
natural key; add back a UNIQUE constraint on (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) to prevent duplicate bindings. Modify the AM_SCOPE_BINDING table
definition (the CREATE TABLE for AM_SCOPE_BINDING) to include UNIQUE (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) alongside PRIMARY KEY (ID) so it matches the
uniqueness semantics used by IDN_OAUTH2_SCOPE_BINDING.
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | ||
| ID INTEGER NOT NULL GENERATED ALWAYS AS IDENTITY (START WITH 1 INCREMENT BY 1), | ||
| API_UUID VARCHAR(255) NOT NULL, | ||
| APPLICATION_ID VARCHAR(20) NOT NULL, | ||
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | ||
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | ||
| HUB_TOPIC VARCHAR(255) NOT NULL, | ||
| HUB_SECRET VARCHAR(2048), | ||
| HUB_LEASE_SECONDS INTEGER, | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||
| PRIMARY KEY (ID) |
There was a problem hiding this comment.
Preserve the previous webhook business key as UNIQUE.
After this change, the table no longer has any uniqueness on the old unsubscription identity, so duplicate unsubscribe rows become valid. Please keep the prior composite key as a UNIQUE constraint alongside the surrogate ID.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/db2.sql`
around lines 3250 - 3260, The table AM_WEBHOOKS_UNSUBSCRIPTION lost its previous
business-key uniqueness; add a UNIQUE constraint on the prior composite business
key (the columns used to identify an unsubscription) alongside the surrogate ID
to prevent duplicate unsubscriptions — for example, alter the CREATE TABLE for
AM_WEBHOOKS_UNSUBSCRIPTION to include a UNIQUE(...) clause referencing the
previous business-key columns (e.g., API_UUID, APPLICATION_ID, TENANT_DOMAIN,
HUB_TOPIC or the exact composite used previously) so the surrogate PRIMARY
KEY(ID) stays and the old composite uniqueness is preserved.
| CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING ( | ||
| ID INTEGER NOT NULL AUTO_INCREMENT, | ||
| SCOPE_ID INTEGER NOT NULL, | ||
| SCOPE_BINDING VARCHAR(255) NOT NULL, | ||
| BINDING_TYPE VARCHAR(255) NOT NULL, | ||
| PRIMARY KEY (ID), | ||
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE |
There was a problem hiding this comment.
Keep the natural key unique after adding ID.
This change removes the old business-key protection from AM_SCOPE_BINDING. With only PRIMARY KEY (ID), duplicate (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) rows become possible.
Suggested fix
CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING (
ID INTEGER NOT NULL AUTO_INCREMENT,
SCOPE_ID INTEGER NOT NULL,
SCOPE_BINDING VARCHAR(255) NOT NULL,
BINDING_TYPE VARCHAR(255) NOT NULL,
+ UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE),
PRIMARY KEY (ID),
FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE
);📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL AUTO_INCREMENT, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE | |
| CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL AUTO_INCREMENT, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE | |
| ); |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/h2.sql`
around lines 2303 - 2309, The new AM_SCOPE_BINDING table drops the previous
business-key uniqueness by only declaring PRIMARY KEY (ID); add a unique
constraint to preserve the natural/business key by declaring UNIQUE (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) on the table definition so duplicates of that
triple cannot be inserted while keeping ID as the surrogate PK; modify the
CREATE TABLE for AM_SCOPE_BINDING to include this UNIQUE constraint referencing
the existing columns SCOPE_ID, SCOPE_BINDING and BINDING_TYPE.
| CREATE TABLE IF NOT EXISTS AM_WEBHOOKS_UNSUBSCRIPTION ( | ||
| ID INTEGER NOT NULL AUTO_INCREMENT, | ||
| API_UUID VARCHAR(255) NOT NULL, | ||
| APPLICATION_ID VARCHAR(20) NOT NULL, | ||
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | ||
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | ||
| HUB_TOPIC VARCHAR(255) NOT NULL, | ||
| HUB_SECRET VARCHAR(2048), | ||
| HUB_LEASE_SECONDS INTEGER, | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||
| PRIMARY KEY (ID) |
There was a problem hiding this comment.
Preserve the previous webhook business key as UNIQUE.
Using ID as the sole key here drops the old unsubscription uniqueness guarantee, so the same webhook unsubscribe can now be stored multiple times. Please retain the prior composite key as a UNIQUE constraint.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/h2.sql`
around lines 2467 - 2477, The new AM_WEBHOOKS_UNSUBSCRIPTION table definition
removed the previous composite business key, allowing duplicate unsubscriptions;
add a UNIQUE constraint on the original composite columns to preserve that
uniqueness (e.g. add UNIQUE (API_UUID, APPLICATION_ID, TENANT_DOMAIN,
HUB_CALLBACK_URL, HUB_TOPIC) in the CREATE TABLE for AM_WEBHOOKS_UNSUBSCRIPTION,
optionally naming the constraint like
UNQ_AM_WEBHOOKS_UNSUBSCRIPTION_BUSINESSKEY) so the combination of those fields
cannot be inserted more than once.
| ID INTEGER NOT NULL IDENTITY, | ||
| SCOPE_ID INTEGER NOT NULL, | ||
| SCOPE_BINDING VARCHAR(255) NOT NULL, | ||
| BINDING_TYPE VARCHAR(255) NOT NULL, | ||
| PRIMARY KEY (ID), | ||
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE |
There was a problem hiding this comment.
Restore business-key uniqueness for AM_SCOPE_BINDING.
Switching this table to PRIMARY KEY (ID) without a replacement UNIQUE constraint now allows duplicate (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) rows. That weakens data integrity and changes the semantics of scope binding lookups.
Suggested fix
CREATE TABLE AM_SCOPE_BINDING (
ID INTEGER NOT NULL IDENTITY,
SCOPE_ID INTEGER NOT NULL,
SCOPE_BINDING VARCHAR(255) NOT NULL,
BINDING_TYPE VARCHAR(255) NOT NULL,
+ UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE),
PRIMARY KEY (ID),
FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE
);📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| ID INTEGER NOT NULL IDENTITY, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE | |
| ID INTEGER NOT NULL IDENTITY, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mssql.sql`
around lines 2564 - 2569, The AM_SCOPE_BINDING table lost its business-key
uniqueness when it was changed to PRIMARY KEY (ID), allowing duplicate
(SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) rows; restore data integrity by adding a
UNIQUE constraint or unique index on the triple (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) for the AM_SCOPE_BINDING table (update the SQL in mssql.sql near
the table definition) so that inserts/updates cannot create duplicates while
keeping the surrogate ID primary key.
| CREATE TABLE AM_SCOPE_BINDING ( | ||
| ID INTEGER NOT NULL, | ||
| SCOPE_ID INTEGER NOT NULL, | ||
| SCOPE_BINDING VARCHAR2(255) NOT NULL, | ||
| BINDING_TYPE VARCHAR2(255) NOT NULL, | ||
| PRIMARY KEY (ID), | ||
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) |
There was a problem hiding this comment.
Keep the old binding tuple unique.
Switching AM_SCOPE_BINDING to PRIMARY KEY (ID) here drops the only uniqueness guarantee on (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), so identical bindings can now be inserted multiple times. If the surrogate key is needed for ORM compatibility, keep the previous business key as a UNIQUE constraint alongside ID.
Suggested fix
CREATE TABLE AM_SCOPE_BINDING (
ID INTEGER NOT NULL,
SCOPE_ID INTEGER NOT NULL,
SCOPE_BINDING VARCHAR2(255) NOT NULL,
BINDING_TYPE VARCHAR2(255) NOT NULL,
PRIMARY KEY (ID),
+ UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE),
FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE)📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| CREATE TABLE AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR2(255) NOT NULL, | |
| BINDING_TYPE VARCHAR2(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) | |
| CREATE TABLE AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR2(255) NOT NULL, | |
| BINDING_TYPE VARCHAR2(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_rac.sql`
around lines 3392 - 3398, The CREATE TABLE for AM_SCOPE_BINDING replaced the
business key with a surrogate PK (ID) but removed uniqueness on the original
tuple; update the DDL to keep ID as PRIMARY KEY and add a UNIQUE constraint on
(SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) so duplicate bindings cannot be
inserted; modify the AM_SCOPE_BINDING definition to include a UNIQUE (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) clause while retaining the FOREIGN KEY on SCOPE_ID
and PRIMARY KEY (ID).
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | ||
| ID INTEGER NOT NULL, | ||
| API_UUID VARCHAR(255) NOT NULL, | ||
| APPLICATION_ID VARCHAR(20) NOT NULL, | ||
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | ||
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | ||
| HUB_TOPIC VARCHAR(255) NOT NULL, | ||
| HUB_SECRET VARCHAR(2048), | ||
| HUB_LEASE_SECONDS INTEGER, | ||
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP) | ||
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP, | ||
| PRIMARY KEY (ID)) |
There was a problem hiding this comment.
Retain the previous webhook business-key uniqueness.
Replacing the composite key with PRIMARY KEY (ID) alone changes the table semantics: duplicate unsubscribe rows for the same webhook can now be stored, and the old key index disappears. Please keep the previous composite key columns as a UNIQUE constraint in addition to the surrogate ID.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_rac.sql`
around lines 3576 - 3586, The table AM_WEBHOOKS_UNSUBSCRIPTION currently uses
only PRIMARY KEY (ID) which removes the previous business-key uniqueness; add
back a UNIQUE constraint on the composite business-key columns (API_UUID,
APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL, HUB_TOPIC) so duplicates cannot
be inserted while keeping the surrogate ID primary key (i.e., keep PRIMARY KEY
(ID) and add UNIQUE(...) on those columns), ensuring the constraint name is
descriptive and consistent with existing naming conventions.
| CREATE TABLE AM_SCOPE_BINDING ( | ||
| ID INTEGER NOT NULL, | ||
| SCOPE_ID INTEGER NOT NULL, | ||
| SCOPE_BINDING VARCHAR2(255) NOT NULL, | ||
| BINDING_TYPE VARCHAR2(255) NOT NULL, | ||
| PRIMARY KEY (ID), | ||
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) | ||
| / |
There was a problem hiding this comment.
Missing UNIQUE constraint on natural key columns.
When switching from a composite primary key to a surrogate ID, a UNIQUE constraint should be added on the previous natural key columns to preserve data integrity. Without it, duplicate scope bindings (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) can now be inserted.
For consistency, note that the similar IDN_OAUTH2_SCOPE_BINDING table at line 289 includes UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE).
Proposed fix
CREATE TABLE AM_SCOPE_BINDING (
ID INTEGER NOT NULL,
SCOPE_ID INTEGER NOT NULL,
SCOPE_BINDING VARCHAR2(255) NOT NULL,
BINDING_TYPE VARCHAR2(255) NOT NULL,
PRIMARY KEY (ID),
+ UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE),
FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE)📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| CREATE TABLE AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR2(255) NOT NULL, | |
| BINDING_TYPE VARCHAR2(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) | |
| / | |
| CREATE TABLE AM_SCOPE_BINDING ( | |
| ID INTEGER NOT NULL, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR2(255) NOT NULL, | |
| BINDING_TYPE VARCHAR2(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE) | |
| / |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql`
around lines 3617 - 3624, The AM_SCOPE_BINDING table now uses a surrogate ID but
lacks a UNIQUE constraint on the former natural key, allowing duplicate entries;
update the AM_SCOPE_BINDING DDL to add a UNIQUE constraint on (SCOPE_ID,
SCOPE_BINDING, BINDING_TYPE) so those three columns remain unique (mirror the
constraint used by IDN_OAUTH2_SCOPE_BINDING), ensuring the UNIQUE is declared
for AM_SCOPE_BINDING alongside the PRIMARY KEY(ID).
| CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING ( | ||
| ID INTEGER DEFAULT NEXTVAL('AM_SCOPE_BINDING_PK_SEQ') NOT NULL, | ||
| SCOPE_ID INTEGER NOT NULL, | ||
| SCOPE_BINDING VARCHAR(255) NOT NULL, | ||
| BINDING_TYPE VARCHAR(255) NOT NULL, | ||
| PRIMARY KEY (ID), | ||
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE |
There was a problem hiding this comment.
Preserve uniqueness on the original scope-binding key.
PRIMARY KEY (ID) is fine for the surrogate key, but without also keeping (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) unique, this table now accepts duplicate bindings that the old key structure would have rejected.
Suggested fix
CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING (
ID INTEGER DEFAULT NEXTVAL('AM_SCOPE_BINDING_PK_SEQ') NOT NULL,
SCOPE_ID INTEGER NOT NULL,
SCOPE_BINDING VARCHAR(255) NOT NULL,
BINDING_TYPE VARCHAR(255) NOT NULL,
PRIMARY KEY (ID),
+ UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE),
FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE
);📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING ( | |
| ID INTEGER DEFAULT NEXTVAL('AM_SCOPE_BINDING_PK_SEQ') NOT NULL, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE | |
| CREATE TABLE IF NOT EXISTS AM_SCOPE_BINDING ( | |
| ID INTEGER DEFAULT NEXTVAL('AM_SCOPE_BINDING_PK_SEQ') NOT NULL, | |
| SCOPE_ID INTEGER NOT NULL, | |
| SCOPE_BINDING VARCHAR(255) NOT NULL, | |
| BINDING_TYPE VARCHAR(255) NOT NULL, | |
| PRIMARY KEY (ID), | |
| UNIQUE (SCOPE_ID, SCOPE_BINDING, BINDING_TYPE), | |
| FOREIGN KEY (SCOPE_ID) REFERENCES AM_SCOPE(SCOPE_ID) ON DELETE CASCADE | |
| ); |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/postgresql.sql`
around lines 2665 - 2671, The table AM_SCOPE_BINDING currently only has a
surrogate primary key ID which allows duplicate logical bindings; add a
uniqueness constraint (or unique index) on the tuple (SCOPE_ID, SCOPE_BINDING,
BINDING_TYPE) to restore the original uniqueness semantics—modify the
AM_SCOPE_BINDING DDL to include a UNIQUE constraint on those three columns (or
create a UNIQUE INDEX on SCOPE_ID, SCOPE_BINDING, BINDING_TYPE) and ensure the
constraint name is descriptive (e.g., AM_SCOPE_BINDING_UQ) so duplicate
(scope_id, scope_binding, binding_type) rows are rejected.
| CREATE TABLE IF NOT EXISTS AM_WEBHOOKS_UNSUBSCRIPTION ( | ||
| ID INTEGER DEFAULT NEXTVAL('AM_WEBHOOKS_UNSUBSCRIPTION_PK_SEQ') NOT NULL, | ||
| API_UUID VARCHAR(255) NOT NULL, | ||
| APPLICATION_ID VARCHAR(20) NOT NULL, | ||
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | ||
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | ||
| HUB_TOPIC VARCHAR(255) NOT NULL, | ||
| HUB_SECRET VARCHAR(2048), | ||
| HUB_LEASE_SECONDS INTEGER, | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||
| PRIMARY KEY (ID) |
There was a problem hiding this comment.
Don’t drop the old webhook uniqueness when adding ID.
This changes AM_WEBHOOKS_UNSUBSCRIPTION from a composite-key table to an ID-only key, which means duplicate unsubscribe rows can now be recorded for the same logical webhook entry. Please retain the previous composite business key as a UNIQUE constraint.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/postgresql.sql`
around lines 2829 - 2839, The CREATE TABLE for AM_WEBHOOKS_UNSUBSCRIPTION
replaced the previous composite business key with a surrogate ID and thus lost
uniqueness; restore the original composite uniqueness by adding a UNIQUE
constraint (or unique index) on the combination of API_UUID, APPLICATION_ID,
TENANT_DOMAIN, HUB_CALLBACK_URL and HUB_TOPIC in the AM_WEBHOOKS_UNSUBSCRIPTION
definition (or immediately after creation) so the table keeps the old
business-key uniqueness while still having the ID primary key.
There was a problem hiding this comment.
Actionable comments posted: 3
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql`:
- Around line 2639-2650: Add a UNIQUE constraint on the natural key for
AM_WEBHOOKS_UNSUBSCRIPTION to prevent duplicate unsubscription rows; modify the
CREATE TABLE for AM_WEBHOOKS_UNSUBSCRIPTION to include a UNIQUE(...) index
covering (API_UUID, APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL, HUB_TOPIC)
and apply the same change to all dialect-specific SQL files (mysql, oracle,
postgresql, mssql) so updateUnSubscription() cannot insert duplicate requests
for the same webhook.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql`:
- Around line 3825-3836: The AM_WEBHOOKS_UNSUBSCRIPTION table lacks a UNIQUE
constraint on its natural key allowing duplicate unsubscription records; add a
UNIQUE constraint on the natural key columns (API_UUID, APPLICATION_ID,
HUB_CALLBACK_URL, HUB_TOPIC) in the CREATE TABLE definition for
AM_WEBHOOKS_UNSUBSCRIPTION so the DB enforces uniqueness for each unsubscription
event (ensure the constraint name is descriptive, e.g.,
UNQ_AM_WEBHOOKS_UNSUBSCRIPTION_API_APP_CALLBACK_TOPIC).
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql`:
- Around line 3824-3846: Add a UNIQUE constraint on the natural key for
AM_WEBHOOKS_UNSUBSCRIPTION to prevent duplicate unsubscriptions: alter the
AM_WEBHOOKS_UNSUBSCRIPTION table definition to include a UNIQUE constraint/index
over (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC) so those four
columns are enforced as unique while keeping the surrogate ID (and existing
SEQUENCE/ TRIGGER) unchanged; apply the same change to the corresponding files
for other dialects (oracle_rac.sql, oracle_23c.sql, mysql.sql, postgresql.sql)
using the appropriate dialect-specific syntax for creating a unique
constraint/index.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 88a2e49a-e592-479a-a079-14420bfa1afc
📒 Files selected for processing (9)
features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/db2.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/h2.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mssql.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_rac.sqlfeatures/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/postgresql.sql
| CREATE TABLE IF NOT EXISTS AM_WEBHOOKS_UNSUBSCRIPTION ( | ||
| ID INTEGER NOT NULL AUTO_INCREMENT, | ||
| API_UUID VARCHAR(255) NOT NULL, | ||
| APPLICATION_ID VARCHAR(20) NOT NULL, | ||
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | ||
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | ||
| HUB_TOPIC VARCHAR(255) NOT NULL, | ||
| HUB_SECRET VARCHAR(2048), | ||
| HUB_LEASE_SECONDS INTEGER, | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP | ||
| ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||
| PRIMARY KEY (ID) | ||
| )ENGINE=NDB; |
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
# First, let's examine the complete webhooks table structure in the SQL file
grep -n "AM_WEBHOOKS" features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql | head -20Repository: wso2/carbon-apimgt
Length of output: 182
🏁 Script executed:
# Get more context around the webhooks tables
sed -n '2620,2660p' features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sqlRepository: wso2/carbon-apimgt
Length of output: 1668
🏁 Script executed:
# Search for code that inserts into or queries AM_WEBHOOKS_UNSUBSCRIPTION
find . -type f \( -name "*.java" -o -name "*.js" -o -name "*.py" \) -exec grep -l "AM_WEBHOOKS_UNSUBSCRIPTION" {} \;Repository: wso2/carbon-apimgt
Length of output: 184
🏁 Script executed:
# Search for references to webhooks unsubscription in the codebase
rg "WEBHOOKS_UNSUBSCRIPTION" --type java -C 3Repository: wso2/carbon-apimgt
Length of output: 1492
🏁 Script executed:
# Look for all references to unsubscription processing
rg "WEBHOOKS_UNSUBSCRIPTION|unsubscription" --type java -B 2 -A 5 | head -100Repository: wso2/carbon-apimgt
Length of output: 9040
🏁 Script executed:
# Check what SQL operations are performed on the unsubscription table
grep -r "AM_WEBHOOKS_UNSUBSCRIPTION" components/ --include="*.java" -B 2 -A 2Repository: wso2/carbon-apimgt
Length of output: 1073
🏁 Script executed:
# Look for any webhook unsubscription logic or handlers
rg "unsubscribe|Unsubscribe" --type java -l | head -10Repository: wso2/carbon-apimgt
Length of output: 1308
🏁 Script executed:
# Check for any SQL constraint definitions or indexes on webhook tables in other SQL dialects
find . -name "*.sql" -exec grep -l "WEBHOOKS_UNSUBSCRIPTION" {} \;Repository: wso2/carbon-apimgt
Length of output: 1317
🏁 Script executed:
# Look at WebhooksDAO to see complete unsubscription processing logic
cat components/apimgt/org.wso2.carbon.apimgt.impl/src/main/java/org/wso2/carbon/apimgt/impl/dao/WebhooksDAO.java | grep -A 20 "updateUnSubscription\|ADD_UNSUBSCRIPTION"Repository: wso2/carbon-apimgt
Length of output: 2553
🏁 Script executed:
# Check for any SELECT queries on unsubscription table
grep -r "AM_WEBHOOKS_UNSUBSCRIPTION" components/ --include="*.java" | grep -i selectRepository: wso2/carbon-apimgt
Length of output: 44
🏁 Script executed:
# Check how unsubscription records are consumed/processed
grep -r "AM_WEBHOOKS_UNSUBSCRIPTION" components/ --include="*.java"Repository: wso2/carbon-apimgt
Length of output: 284
🏁 Script executed:
# Check MySQL dialect to see if they're different
sed -n '2620,2660p' features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql.sqlRepository: wso2/carbon-apimgt
Length of output: 1748
🏁 Script executed:
# Check Oracle dialect
grep -A 20 "CREATE TABLE.*AM_WEBHOOKS_UNSUBSCRIPTION" features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sqlRepository: wso2/carbon-apimgt
Length of output: 927
🏁 Script executed:
# Check PostgreSQL dialect
grep -A 20 "CREATE TABLE.*AM_WEBHOOKS_UNSUBSCRIPTION" features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/postgresql.sqlRepository: wso2/carbon-apimgt
Length of output: 1002
Add a UNIQUE constraint on the natural key columns to prevent duplicate unsubscription requests.
The AM_WEBHOOKS_UNSUBSCRIPTION table stores pending unsubscription requests that are inserted via updateUnSubscription(). Without a UNIQUE constraint on the natural key (API_UUID, APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL, HUB_TOPIC), duplicate unsubscription requests can be inserted if the method is called multiple times for the same webhook.
This would lead to duplicate processing attempts being sent to webhook endpoints, causing data integrity issues in webhook lifecycle management. The pattern is consistent across all database dialects (MySQL, Oracle, PostgreSQL).
Proposed fix
CREATE TABLE IF NOT EXISTS AM_WEBHOOKS_UNSUBSCRIPTION (
ID INTEGER NOT NULL AUTO_INCREMENT,
API_UUID VARCHAR(255) NOT NULL,
APPLICATION_ID VARCHAR(20) NOT NULL,
TENANT_DOMAIN VARCHAR(255) NOT NULL,
HUB_CALLBACK_URL VARCHAR(1024) NOT NULL,
HUB_TOPIC VARCHAR(255) NOT NULL,
HUB_SECRET VARCHAR(2048),
HUB_LEASE_SECONDS INTEGER,
ADDED_AT TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
- PRIMARY KEY (ID)
+ PRIMARY KEY (ID),
+ UNIQUE (API_UUID, APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL, HUB_TOPIC)
)ENGINE=NDB;Apply the same fix to all SQL dialect files (mysql.sql, oracle.sql, postgresql.sql, mssql.sql, etc.).
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/mysql_cluster.sql`
around lines 2639 - 2650, Add a UNIQUE constraint on the natural key for
AM_WEBHOOKS_UNSUBSCRIPTION to prevent duplicate unsubscription rows; modify the
CREATE TABLE for AM_WEBHOOKS_UNSUBSCRIPTION to include a UNIQUE(...) index
covering (API_UUID, APPLICATION_ID, TENANT_DOMAIN, HUB_CALLBACK_URL, HUB_TOPIC)
and apply the same change to all dialect-specific SQL files (mysql, oracle,
postgresql, mssql) so updateUnSubscription() cannot insert duplicate requests
for the same webhook.
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | ||
| ID INTEGER NOT NULL, | ||
| API_UUID VARCHAR(255) NOT NULL, | ||
| APPLICATION_ID VARCHAR(20) NOT NULL, | ||
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | ||
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | ||
| HUB_TOPIC VARCHAR(255) NOT NULL, | ||
| HUB_SECRET VARCHAR(2048), | ||
| HUB_LEASE_SECONDS INTEGER, | ||
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP) | ||
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP, | ||
| PRIMARY KEY (ID)) | ||
| / |
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
# Check AM_WEBHOOKS_UNSUBSCRIPTION definition across all SQL dialect files for UNIQUE constraints
for f in $(fd -e sql . features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/); do
echo "=== $f ==="
awk '/CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION/,/^[\/;]/' "$f" | head -20
doneRepository: wso2/carbon-apimgt
Length of output: 3839
🏁 Script executed:
#!/bin/bash
# Check IDN_OAUTH2_TOKEN_BINDING and AM_API_REVISION_METADATA in oracle_23c.sql
echo "=== Checking IDN_OAUTH2_TOKEN_BINDING ==="
grep -A 20 "CREATE TABLE IDN_OAUTH2_TOKEN_BINDING" features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql
echo ""
echo "=== Checking AM_API_REVISION_METADATA ==="
grep -A 20 "CREATE TABLE AM_API_REVISION_METADATA" features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sqlRepository: wso2/carbon-apimgt
Length of output: 1790
🏁 Script executed:
#!/bin/bash
# Search for any UNIQUE constraints in the AM_WEBHOOKS_UNSUBSCRIPTION region
echo "=== Full AM_WEBHOOKS_UNSUBSCRIPTION + surrounding context ==="
sed -n '3820,3850p' features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sqlRepository: wso2/carbon-apimgt
Length of output: 1229
🏁 Script executed:
#!/bin/bash
# Check if other dialect files have UNIQUE constraints on AM_WEBHOOKS_UNSUBSCRIPTION
echo "=== Checking for UNIQUE constraints in AM_WEBHOOKS_UNSUBSCRIPTION across all dialects ==="
for f in features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/{oracle,mysql,postgresql,mssql}.sql; do
if [ -f "$f" ]; then
echo "File: $(basename $f)"
awk '/CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION/,/^[\/;]/' "$f" | grep -i unique && echo "Found UNIQUE" || echo "No UNIQUE constraint"
fi
doneRepository: wso2/carbon-apimgt
Length of output: 971
🏁 Script executed:
#!/bin/bash
# Check recent commits affecting oracle_23c.sql for AM_WEBHOOKS_UNSUBSCRIPTION
git log --oneline -20 -- features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql
echo ""
echo "=== Checking for recent changes to AM_WEBHOOKS_UNSUBSCRIPTION ==="
git log -p --follow -- features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql | grep -A 20 -B 5 "AM_WEBHOOKS_UNSUBSCRIPTION" | head -50Repository: wso2/carbon-apimgt
Length of output: 211
🏁 Script executed:
#!/bin/bash
# Search for any mention of webhook unsubscription schema changes
git log --all --grep="webhook" --grep="unsubscription" --grep="composite.*key" -i --oneline | head -10Repository: wso2/carbon-apimgt
Length of output: 842
🏁 Script executed:
#!/bin/bash
# Get the diff for the commit that added primary keys
git show 080861bb5f3 -- features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql | grep -A 30 -B 5 "AM_WEBHOOKS_UNSUBSCRIPTION"Repository: wso2/carbon-apimgt
Length of output: 2019
🏁 Script executed:
#!/bin/bash
# Alternative: check if there's an older version without PRIMARY KEY
git show 080861bb5f3^:features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql 2>/dev/null | grep -A 15 "CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION"Repository: wso2/carbon-apimgt
Length of output: 44
Missing UNIQUE constraint on natural key may allow duplicate unsubscription records.
While this table is newly created (not refactored from a previous composite key), it lacks a UNIQUE constraint on its natural key unlike similar tables in the same file (IDN_OAUTH2_TOKEN_BINDING has UNIQUE (TOKEN_ID, TOKEN_BINDING_TYPE, TOKEN_BINDING_VALUE) and AM_API_REVISION_METADATA has UNIQUE (API_UUID, REVISION_UUID)). Without such a constraint, the same unsubscription event (same API, application, callback URL, and topic) can be inserted multiple times, potentially causing duplicate processing.
Add a UNIQUE constraint on the columns that form the natural key—likely API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC—to maintain data integrity.
Proposed fix
CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION (
ID INTEGER NOT NULL,
API_UUID VARCHAR(255) NOT NULL,
APPLICATION_ID VARCHAR(20) NOT NULL,
TENANT_DOMAIN VARCHAR(255) NOT NULL,
HUB_CALLBACK_URL VARCHAR(1024) NOT NULL,
HUB_TOPIC VARCHAR(255) NOT NULL,
HUB_SECRET VARCHAR(2048),
HUB_LEASE_SECONDS INTEGER,
ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
- PRIMARY KEY (ID))
+ PRIMARY KEY (ID),
+ UNIQUE (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC))📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | |
| ID INTEGER NOT NULL, | |
| API_UUID VARCHAR(255) NOT NULL, | |
| APPLICATION_ID VARCHAR(20) NOT NULL, | |
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | |
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | |
| HUB_TOPIC VARCHAR(255) NOT NULL, | |
| HUB_SECRET VARCHAR(2048), | |
| HUB_LEASE_SECONDS INTEGER, | |
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP) | |
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP, | |
| PRIMARY KEY (ID)) | |
| / | |
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | |
| ID INTEGER NOT NULL, | |
| API_UUID VARCHAR(255) NOT NULL, | |
| APPLICATION_ID VARCHAR(20) NOT NULL, | |
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | |
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | |
| HUB_TOPIC VARCHAR(255) NOT NULL, | |
| HUB_SECRET VARCHAR(2048), | |
| HUB_LEASE_SECONDS INTEGER, | |
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP, | |
| PRIMARY KEY (ID), | |
| UNIQUE (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC)) | |
| / |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle_23c.sql`
around lines 3825 - 3836, The AM_WEBHOOKS_UNSUBSCRIPTION table lacks a UNIQUE
constraint on its natural key allowing duplicate unsubscription records; add a
UNIQUE constraint on the natural key columns (API_UUID, APPLICATION_ID,
HUB_CALLBACK_URL, HUB_TOPIC) in the CREATE TABLE definition for
AM_WEBHOOKS_UNSUBSCRIPTION so the DB enforces uniqueness for each unsubscription
event (ensure the constraint name is descriptive, e.g.,
UNQ_AM_WEBHOOKS_UNSUBSCRIPTION_API_APP_CALLBACK_TOPIC).
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | ||
| ID INTEGER NOT NULL, | ||
| API_UUID VARCHAR(255) NOT NULL, | ||
| APPLICATION_ID VARCHAR(20) NOT NULL, | ||
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | ||
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | ||
| HUB_TOPIC VARCHAR(255) NOT NULL, | ||
| HUB_SECRET VARCHAR(2048), | ||
| HUB_LEASE_SECONDS INTEGER, | ||
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP) | ||
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP, | ||
| PRIMARY KEY (ID)) | ||
| / | ||
| CREATE SEQUENCE AM_WEBHOOKS_UNSUBSCRIPTION_SEQ START WITH 1 INCREMENT BY 1 NOCACHE | ||
| / | ||
| CREATE OR REPLACE TRIGGER AM_WEBHOOKS_UNSUBSCRIPTION_TRIG | ||
| BEFORE INSERT | ||
| ON AM_WEBHOOKS_UNSUBSCRIPTION | ||
| REFERENCING NEW AS NEW | ||
| FOR EACH ROW | ||
| BEGIN | ||
| SELECT AM_WEBHOOKS_UNSUBSCRIPTION_SEQ.nextval INTO :NEW.ID FROM dual; | ||
| END; | ||
| / |
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
# Check other SQL dialect files for this table to see if any have UNIQUE constraints
rg -n "AM_WEBHOOKS_UNSUBSCRIPTION" --type sql -A 15 | head -100Repository: wso2/carbon-apimgt
Length of output: 12967
Add UNIQUE constraint on natural key columns.
Across all database dialects (PostgreSQL, MySQL, Oracle), the surrogate ID replaces the composite key without preserving uniqueness on the natural key. This allows duplicate unsubscription records for the same webhook (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC) to be inserted, compromising data integrity.
Proposed fix
CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION (
ID INTEGER NOT NULL,
API_UUID VARCHAR(255) NOT NULL,
APPLICATION_ID VARCHAR(20) NOT NULL,
TENANT_DOMAIN VARCHAR(255) NOT NULL,
HUB_CALLBACK_URL VARCHAR(1024) NOT NULL,
HUB_TOPIC VARCHAR(255) NOT NULL,
HUB_SECRET VARCHAR(2048),
HUB_LEASE_SECONDS INTEGER,
ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
- PRIMARY KEY (ID))
+ PRIMARY KEY (ID),
+ UNIQUE (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC))Apply the same fix to all database dialect files: oracle.sql, oracle_rac.sql, oracle_23c.sql, mysql.sql, and postgresql.sql.
📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | |
| ID INTEGER NOT NULL, | |
| API_UUID VARCHAR(255) NOT NULL, | |
| APPLICATION_ID VARCHAR(20) NOT NULL, | |
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | |
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | |
| HUB_TOPIC VARCHAR(255) NOT NULL, | |
| HUB_SECRET VARCHAR(2048), | |
| HUB_LEASE_SECONDS INTEGER, | |
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP) | |
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP, | |
| PRIMARY KEY (ID)) | |
| / | |
| CREATE SEQUENCE AM_WEBHOOKS_UNSUBSCRIPTION_SEQ START WITH 1 INCREMENT BY 1 NOCACHE | |
| / | |
| CREATE OR REPLACE TRIGGER AM_WEBHOOKS_UNSUBSCRIPTION_TRIG | |
| BEFORE INSERT | |
| ON AM_WEBHOOKS_UNSUBSCRIPTION | |
| REFERENCING NEW AS NEW | |
| FOR EACH ROW | |
| BEGIN | |
| SELECT AM_WEBHOOKS_UNSUBSCRIPTION_SEQ.nextval INTO :NEW.ID FROM dual; | |
| END; | |
| / | |
| CREATE TABLE AM_WEBHOOKS_UNSUBSCRIPTION ( | |
| ID INTEGER NOT NULL, | |
| API_UUID VARCHAR(255) NOT NULL, | |
| APPLICATION_ID VARCHAR(20) NOT NULL, | |
| TENANT_DOMAIN VARCHAR(255) NOT NULL, | |
| HUB_CALLBACK_URL VARCHAR(1024) NOT NULL, | |
| HUB_TOPIC VARCHAR(255) NOT NULL, | |
| HUB_SECRET VARCHAR(2048), | |
| HUB_LEASE_SECONDS INTEGER, | |
| ADDED_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP, | |
| PRIMARY KEY (ID), | |
| UNIQUE (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC)) | |
| / | |
| CREATE SEQUENCE AM_WEBHOOKS_UNSUBSCRIPTION_SEQ START WITH 1 INCREMENT BY 1 NOCACHE | |
| / | |
| CREATE OR REPLACE TRIGGER AM_WEBHOOKS_UNSUBSCRIPTION_TRIG | |
| BEFORE INSERT | |
| ON AM_WEBHOOKS_UNSUBSCRIPTION | |
| REFERENCING NEW AS NEW | |
| FOR EACH ROW | |
| BEGIN | |
| SELECT AM_WEBHOOKS_UNSUBSCRIPTION_SEQ.nextval INTO :NEW.ID FROM dual; | |
| END; | |
| / |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In
`@features/apimgt/org.wso2.carbon.apimgt.core.feature/src/main/resources/sql/oracle.sql`
around lines 3824 - 3846, Add a UNIQUE constraint on the natural key for
AM_WEBHOOKS_UNSUBSCRIPTION to prevent duplicate unsubscriptions: alter the
AM_WEBHOOKS_UNSUBSCRIPTION table definition to include a UNIQUE constraint/index
over (API_UUID, APPLICATION_ID, HUB_CALLBACK_URL, HUB_TOPIC) so those four
columns are enforced as unique while keeping the surrogate ID (and existing
SEQUENCE/ TRIGGER) unchanged; apply the same change to the corresponding files
for other dialects (oracle_rac.sql, oracle_23c.sql, mysql.sql, postgresql.sql)
using the appropriate dialect-specific syntax for creating a unique
constraint/index.
Description
This pull request updates the database schema scripts for multiple RDBMSs (MySQL, H2, MSSQL, Oracle, DB2) to add an auto-incrementing primary key column (
ID) to several tables that previously lacked a simple integer primary key. For Oracle and Oracle 23c, it also adds the necessary sequences and triggers to support auto-increment behavior. These changes improve data integrity, support for ORM frameworks, and ease of referencing rows.The most important changes are:
Schema enhancements:
IDcolumn as an auto-incrementing primary key to the following tables across all supported databases:IDN_OAUTH2_TOKEN_BINDING,AM_SCOPE_BINDING,AM_API_REVISION_METADATA, andAM_WEBHOOKS_UNSUBSCRIPTION. [1] [2] [3] [4] [5] [6] [7] [8] [9] [10] [11] [12] [13] [14] [15] [16] [17] [18] [19] [20] [21] [22] [23] [24]Oracle-specific support:
IDcolumns for the affected tables, ensuring auto-increment behavior. [1] [2] [3] [4] [5]These changes standardize primary key usage across the schema and ensure compatibility and consistency for all supported database platforms.