Skip to content

Commit c6f47be

Browse files
committed
Add LinkedIn import, alter route, and sample CSV
Add endpoints and sample data to support importing LinkedIn CSVs and altering the queue schema. - Add app/api/queue/routes/import_linkedin.py: POST /queue/import/linkedin reads a linkedin_sample.csv, skips lines starting with 'Notes:', and inserts rows into the queue table (sets created/updated, hidden=false, collection='prospects'). - Add app/api/queue/routes/alter.py: POST /queue/alter/add-column runs an ALTER TABLE to add a column and returns an appropriate meta response; handles 'already exists' errors. - Add sample CSV at app/api/queue/csv/linkedin/linkedin_sample.csv for testing/import. - Update app/api/queue/__init__.py to include the new routers (import_linkedin and alter). - Small change in app/api/queue/routes/get.py: rename response key record_count -> queued and reorder schema/most_recent keys. These changes make it easier to seed the queue from LinkedIn exports and modify the queue schema dynamically.
1 parent 8036e16 commit c6f47be

5 files changed

Lines changed: 92 additions & 4 deletions

File tree

app/api/queue/__init__.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,16 @@
55
from .routes.drop import router as drop_router
66
from .routes.empty import router as empty_router
77
from .routes.get import router as get_router
8+
89
from .routes.create import router as create_router
910

11+
from .routes.import_linkedin import router as import_linkedin_router
12+
from .routes.alter import router as alter_router
13+
1014
router = APIRouter()
1115
router.include_router(drop_router)
1216
router.include_router(empty_router)
1317
router.include_router(get_router)
14-
router.include_router(create_router)
18+
router.include_router(create_router)
19+
router.include_router(import_linkedin_router)
20+
router.include_router(alter_router)
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
First Name,Last Name,URL,Email Address,Company,Position,Connected On
2+
Manny,Okene,https://www.linkedin.com/in/manny-o-462924138,,Premier Group Recruitment,Associate Director,29 Mar 2026
3+
Mark Keers -,Pulse IT Recruitment Ltd,https://www.linkedin.com/in/markkeers,,Pulse IT Recruitment Ltd,IT Recruiter & Managing Director - 07500 734616,26 Mar 2026
4+
Shaun,O'Donnell,https://www.linkedin.com/in/shaunodonnell,,Erin Associates Ltd,Director,12 Mar 2026
5+
Kai,Kemp,https://www.linkedin.com/in/kaikemp97,,Technify Talent,Principal Consultant,04 Mar 2026
6+
James,Ward,https://www.linkedin.com/in/james-ward-echopay,,EchoPay Technology Ltd,Managing Director,04 Mar 2026
7+
Graham,Feegan,https://www.linkedin.com/in/grahamfeegan,,Charles Jenson Recruitment,Recruitment Director,18 Feb 2026
8+
Nabil,Cook,https://www.linkedin.com/in/nabilcook,,OMEGA Solutions,Co-Founder & Technical Director,11 Feb 2026
9+
Oliver,Ward,https://www.linkedin.com/in/oliver-ward-6057a1262,,EchoPay,Customer Success Manager,11 Feb 2026
10+
🟢 Brad,Leaman,https://www.linkedin.com/in/bradleaman,,F5 Consultants,Principal Recruitment Consultant & Co-Founder,08 Feb 2026
11+
Rupal,Gupta,https://www.linkedin.com/in/rupal-gupta-a66975214,,PRACYVA ,Senior IT Recruiter (UK/EU),04 Feb 2026

app/api/queue/routes/alter.py

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
from fastapi import APIRouter, HTTPException, Body
2+
from app.utils.make_meta import make_meta
3+
from app.utils.db import get_db_connection_direct
4+
5+
router = APIRouter()
6+
7+
@router.post("/queue/alter/add-column")
8+
def add_column_to_queue(
9+
column_name: str = Body(..., embed=True),
10+
column_type: str = Body(..., embed=True)
11+
) -> dict:
12+
"""POST /queue/alter/add-column: Add a new column to the queue table."""
13+
try:
14+
conn = get_db_connection_direct()
15+
cursor = conn.cursor()
16+
sql = f'ALTER TABLE queue ADD COLUMN "{column_name}" {column_type};'
17+
cursor.execute(sql)
18+
conn.commit()
19+
conn.close()
20+
return {"meta": make_meta("success", f"Column '{column_name}' added as {column_type}")}
21+
except Exception as e:
22+
msg = str(e)
23+
if 'already exists' in msg:
24+
return {"meta": make_meta("error", f"Column '{column_name}' exists")}
25+
raise HTTPException(status_code=500, detail=msg)

app/api/queue/routes/get.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -38,9 +38,9 @@ def read_queue() -> dict:
3838
return {
3939
"meta": make_meta("success", "Queue table info"),
4040
"data": {
41-
"record_count": record_count,
42-
"schema": schema,
43-
"most_recent": most_recent
41+
"queued": record_count,
42+
"most_recent": most_recent,
43+
"schema": schema
4444
}
4545
}
4646
except Exception as e:
Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
import os
2+
import csv
3+
import time
4+
from fastapi import APIRouter, HTTPException
5+
from app.utils.make_meta import make_meta
6+
from app.utils.db import get_db_connection_direct
7+
8+
router = APIRouter()
9+
10+
@router.post("/queue/import/linkedin")
11+
def import_linkedin_csv() -> dict:
12+
"""POST /queue/import/linkedin: Import data from linkedin_sample.csv into the queue table."""
13+
csv_path = os.path.join(os.path.dirname(__file__), "../csv/linkedin/linkedin_sample.csv")
14+
if not os.path.exists(csv_path):
15+
raise HTTPException(status_code=404, detail="linkedin_sample.csv not found")
16+
try:
17+
conn = get_db_connection_direct()
18+
cursor = conn.cursor()
19+
with open(csv_path, newline='', encoding='utf-8') as csvfile:
20+
reader = csv.DictReader(row for row in csvfile if not row.startswith('Notes:'))
21+
now = int(time.time())
22+
for row in reader:
23+
cursor.execute(
24+
"""
25+
INSERT INTO queue (first_name, last_name, url, email_address, company, position, connected_on, created, updated, hidden, collection)
26+
VALUES (%s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s)
27+
""",
28+
[
29+
row.get('First Name'),
30+
row.get('Last Name'),
31+
row.get('URL'),
32+
row.get('Email Address'),
33+
row.get('Company'),
34+
row.get('Position'),
35+
row.get('Connected On'),
36+
now,
37+
now,
38+
False,
39+
'prospects'
40+
]
41+
)
42+
conn.commit()
43+
conn.close()
44+
return {"meta": make_meta("success", "LinkedIn CSV imported")}
45+
except Exception as e:
46+
raise HTTPException(status_code=500, detail=str(e))

0 commit comments

Comments
 (0)