1
0
mirror of https://github.com/sqlite/sqlite.git synced 2025-08-08 14:02:16 +03:00

Add the Upsert object for holding upsert clause information.

FossilOrigin-Name: d83eaed539b274c2abd650d07522f491865d4917acbb64d05d01b3ba5c3cd446
This commit is contained in:
drh
2018-04-12 13:15:43 +00:00
parent 35e86bf15d
commit 46d2e5c35a
7 changed files with 81 additions and 76 deletions

View File

@@ -1095,6 +1095,7 @@ typedef struct Trigger Trigger;
typedef struct TriggerPrg TriggerPrg;
typedef struct TriggerStep TriggerStep;
typedef struct UnpackedRecord UnpackedRecord;
typedef struct Upsert Upsert;
typedef struct VTable VTable;
typedef struct VtabCtx VtabCtx;
typedef struct Walker Walker;
@@ -2046,7 +2047,6 @@ struct FKey {
#define OE_Fail 3 /* Stop the operation but leave all prior changes */
#define OE_Ignore 4 /* Ignore the error. Do not do the INSERT or UPDATE */
#define OE_Replace 5 /* Delete existing record, then do INSERT or UPDATE */
#define OE_Update 5 /* An UPSERT. Same value as OE_Replace. */
#define OE_Restrict 6 /* OE_Abort for IMMEDIATE, OE_Rollback for DEFERRED */
#define OE_SetNull 7 /* Set the foreign key value to NULL */
@@ -2709,6 +2709,17 @@ struct NameContext {
#define NC_MinMaxAgg 0x1000 /* min/max aggregates seen. See note above */
#define NC_Complex 0x2000 /* True if a function or subquery seen */
/*
** An instance of the following object describes a single ON CONFLICT
** clause in an upsert. A list of these objects may be attached to
** an INSERT statement in order to form an upsert.
*/
struct Upsert {
ExprList *pUpsertTarget; /* Optional description of conflicting index */
ExprList *pUpsertSet; /* The SET clause from an ON CONFLICT UPDATE */
Upsert *pUpsertNext; /* Next ON CONFLICT clause in the list */
};
/*
** An instance of the following structure contains all information
** needed to generate code for a single SELECT statement.
@@ -3208,8 +3219,9 @@ struct TriggerStep {
Select *pSelect; /* SELECT statement or RHS of INSERT INTO SELECT ... */
char *zTarget; /* Target table for DELETE, UPDATE, INSERT */
Expr *pWhere; /* The WHERE clause for DELETE or UPDATE steps */
ExprList *pExprList; /* SET clause for UPDATE or UPSERT. */
ExprList *pExprList; /* SET clause for UPDATE */
IdList *pIdList; /* Column names for INSERT */
Upsert *pUpsert; /* Upsert clauses on an INSERT */
char *zSpan; /* Original SQL text of this command */
TriggerStep *pNext; /* Next in the link-list */
TriggerStep *pLast; /* Last element in link-list. Valid for 1st elem only */
@@ -3741,7 +3753,7 @@ void sqlite3DeleteTable(sqlite3*, Table*);
# define sqlite3AutoincrementBegin(X)
# define sqlite3AutoincrementEnd(X)
#endif
void sqlite3Insert(Parse*, SrcList*, Select*, IdList*, int, ExprList*);
void sqlite3Insert(Parse*, SrcList*, Select*, IdList*, int, Upsert*);
void *sqlite3ArrayAllocate(sqlite3*,void*,int,int*,int*);
IdList *sqlite3IdListAppend(sqlite3*, IdList*, Token*);
int sqlite3IdListIndex(IdList*,const char*);
@@ -3917,7 +3929,7 @@ void sqlite3MaterializeView(Parse*, Table*, Expr*, ExprList*,Expr*,int);
TriggerStep *sqlite3TriggerSelectStep(sqlite3*,Select*,
const char*,const char*);
TriggerStep *sqlite3TriggerInsertStep(sqlite3*,Token*, IdList*,
Select*,u8,ExprList*,
Select*,u8,Upsert*,
const char*,const char*);
TriggerStep *sqlite3TriggerUpdateStep(sqlite3*,Token*,ExprList*, Expr*, u8,
const char*,const char*);
@@ -4257,6 +4269,14 @@ const char *sqlite3JournalModename(int);
#define sqlite3WithPush(x,y,z)
#define sqlite3WithDelete(x,y)
#endif
#ifndef SQLITE_OMIT_UPSERT
void sqlite3UpsertDelete(sqlite3*,Upsert*);
Upsert *sqlite3UpsertDup(sqlite3*,Upsert*);
#else
#define sqlite3UpsertDelete(x,y)
#define sqlite3UpsertDup(x,y) ((Upsert*)0)
#endif
/* Declarations for functions in fkey.c. All of these are replaced by
** no-op macros if OMIT_FOREIGN_KEY is defined. In this case no foreign