1616 5) Query and join data across tables
1717 6) Clean up (delete tables)
1818
19+ Note: The last step (cleanup) automatically deletes all demo tables.
20+ Comment out the cleanup() call in run_demo() if you want to keep the
21+ tables in your environment for inspection.
22+
1923Why pandas DataFrames?
2024 This example uses client.dataframe (pandas) instead of raw dict/list CRUD
2125 because DataFrames provide significant advantages for multi-record operations:
@@ -100,19 +104,19 @@ def run_demo(client):
100104 print (f"[INFO] Output folder: { OUTPUT_DIR .resolve ()} " )
101105
102106 # -- Step 1: Create 4 tables --
103- step1_create_tables (client )
107+ primary_name_col = step1_create_tables (client )
104108
105109 # -- Step 2: Create relationships --
106110 step2_create_relationships (client )
107111
108112 # -- Step 3: Populate with sample data --
109- customer_ids , project_ids , task_ids = step3_populate_data (client )
113+ customer_ids , project_ids , task_ids = step3_populate_data (client , primary_name_col )
110114
111115 # -- Step 4: Query and analyze --
112- step4_query_and_analyze (client , customer_ids )
116+ step4_query_and_analyze (client , customer_ids , primary_name_col )
113117
114118 # -- Step 5: Update and delete --
115- step5_update_and_delete (client , task_ids )
119+ step5_update_and_delete (client , task_ids , primary_name_col )
116120
117121 # -- Step 6: Cleanup --
118122 cleanup (client )
@@ -134,15 +138,18 @@ def step1_create_tables(client):
134138 print ("-" * 60 )
135139
136140 # Customer table
137- client .tables .create (
141+ result = client .tables .create (
138142 TABLE_CUSTOMER ,
139143 {
140144 f"{ TABLE_CUSTOMER } _Email" : "string" ,
141145 f"{ TABLE_CUSTOMER } _Industry" : "string" ,
142146 f"{ TABLE_CUSTOMER } _Revenue" : "money" ,
143147 },
144148 )
145- print (f"[OK] Created table: { TABLE_CUSTOMER } " )
149+ # The primary name column logical name is returned by tables.create()
150+ # so we know exactly what key to use in create payloads.
151+ primary_name_col = result .primary_name_attribute
152+ print (f"[OK] Created table: { TABLE_CUSTOMER } (primary column: { primary_name_col } )" )
146153
147154 # Project table
148155 client .tables .create (
@@ -177,6 +184,9 @@ def step1_create_tables(client):
177184 )
178185 print (f"[OK] Created table: { TABLE_TIMEENTRY } " )
179186 print (f"[OK] All 4 tables created with prefix '{ PREFIX } '" )
187+ print (f"[INFO] Primary name column: '{ primary_name_col } '" )
188+
189+ return primary_name_col
180190
181191
182192# ================================================================
@@ -225,7 +235,7 @@ def step2_create_relationships(client):
225235# ================================================================
226236
227237
228- def step3_populate_data (client ):
238+ def step3_populate_data (client , primary_name_col ):
229239 """Create sample records using client.dataframe.create().
230240
231241 Why DataFrames here instead of client.records.create()?
@@ -252,10 +262,8 @@ def step3_populate_data(client):
252262 print ("-" * 60 )
253263
254264 # -- Customers --
255- # Note: The primary column logical name is {prefix}_name (lowercase),
256- # and custom column logical names follow the same lowercase convention.
257- # The SDK lowercases keys automatically, so we use the schema names here.
258- name_col = f"{ PREFIX } _Name"
265+ # Use the primary name column returned by tables.create()
266+ name_col = primary_name_col
259267 customers_df = pd .DataFrame (
260268 [
261269 {
@@ -364,15 +372,15 @@ def step3_populate_data(client):
364372# ================================================================
365373
366374
367- def step4_query_and_analyze (client , customer_ids ):
375+ def step4_query_and_analyze (client , customer_ids , primary_name_col ):
368376 """Query data and demonstrate DataFrame analysis."""
369377 print ("\n " + "-" * 60 )
370378 print ("STEP 4: Query and analyze data" )
371379 print ("-" * 60 )
372380
373381 # Query all projects as a DataFrame
374382 # Note: select uses logical names (lowercase). The SDK lowercases automatically.
375- name_attr = f" { PREFIX } _name" # primary column logical name
383+ name_attr = primary_name_col
376384 projects = client .dataframe .get (
377385 TABLE_PROJECT ,
378386 select = [
@@ -437,7 +445,7 @@ def step4_query_and_analyze(client, customer_ids):
437445# ================================================================
438446
439447
440- def step5_update_and_delete (client , task_ids ):
448+ def step5_update_and_delete (client , task_ids , primary_name_col ):
441449 """Demonstrate update and delete with DataFrames."""
442450 print ("\n " + "-" * 60 )
443451 print ("STEP 5: Update and delete records" )
@@ -461,10 +469,9 @@ def step5_update_and_delete(client, task_ids):
461469 print (f"[OK] Deleted 1 task" )
462470
463471 # Verify
464- name_attr = f"{ PREFIX } _name"
465472 remaining = client .dataframe .get (
466473 TABLE_TASK ,
467- select = [name_attr , status_col ],
474+ select = [primary_name_col , status_col ],
468475 )
469476 print (f"\n Remaining tasks ({ len (remaining )} ):" )
470477 print (f"{ remaining .to_string (index = False )} " )
0 commit comments