Compare commits
2 Commits
705a99d415
...
eb2cb72ea4
| Author | SHA1 | Date | |
|---|---|---|---|
| eb2cb72ea4 | |||
| 2a0d231597 |
11
doc/prompts/12 csv import
Normal file
11
doc/prompts/12 csv import
Normal file
@ -0,0 +1,11 @@
|
||||
Please make script to import following csv to Customer model
|
||||
|
||||
City,Name,Website URL,Email
|
||||
"Tokyo","teamLab Planets TOKYO","http://www.teamlab.art/e/planets/","null"
|
||||
"Tokyo","Tokyo National Museum","http://www.tnm.jp/","null"
|
||||
"Tokyo","Nezu Museum","http://www.nezu-muse.or.jp/","null"
|
||||
|
||||
- Name should be unique.
|
||||
- Also if there are same email address skip the row.
|
||||
|
||||
Create new branch features/csvimport and commit when you finished
|
||||
6
package-lock.json
generated
6
package-lock.json
generated
@ -19,6 +19,7 @@
|
||||
"@editorjs/paragraph": "^2.11.7",
|
||||
"@editorjs/quote": "^2.7.6",
|
||||
"bcrypt": "^5.1.1",
|
||||
"csv-parse": "^5.6.0",
|
||||
"jsonwebtoken": "^9.0.2",
|
||||
"mysql2": "^3.13.0",
|
||||
"next": "15.2.2",
|
||||
@ -2764,6 +2765,11 @@
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/csv-parse": {
|
||||
"version": "5.6.0",
|
||||
"resolved": "https://registry.npmjs.org/csv-parse/-/csv-parse-5.6.0.tgz",
|
||||
"integrity": "sha512-l3nz3euub2QMg5ouu5U09Ew9Wf6/wQ8I++ch1loQ0ljmzhmfZYrH9fflS22i/PQEvsPvxCwxgz5q7UB8K1JO4Q=="
|
||||
},
|
||||
"node_modules/damerau-levenshtein": {
|
||||
"version": "1.0.8",
|
||||
"resolved": "https://registry.npmjs.org/damerau-levenshtein/-/damerau-levenshtein-1.0.8.tgz",
|
||||
|
||||
@ -8,7 +8,8 @@
|
||||
"start": "next start",
|
||||
"lint": "next lint",
|
||||
"create-test-user": "npx ts-node -P tsconfig.scripts.json src/scripts/create-test-user.ts",
|
||||
"reset-database": "npx ts-node -P tsconfig.scripts.json src/scripts/reset-database.ts"
|
||||
"reset-database": "npx ts-node -P tsconfig.scripts.json src/scripts/reset-database.ts",
|
||||
"import-customers": "npx ts-node -P tsconfig.scripts.json src/scripts/import-customers.ts"
|
||||
},
|
||||
"dependencies": {
|
||||
"@editorjs/code": "^2.9.3",
|
||||
@ -22,6 +23,7 @@
|
||||
"@editorjs/paragraph": "^2.11.7",
|
||||
"@editorjs/quote": "^2.7.6",
|
||||
"bcrypt": "^5.1.1",
|
||||
"csv-parse": "^5.6.0",
|
||||
"jsonwebtoken": "^9.0.2",
|
||||
"mysql2": "^3.13.0",
|
||||
"next": "15.2.2",
|
||||
|
||||
108
src/scripts/import-customers.ts
Normal file
108
src/scripts/import-customers.ts
Normal file
@ -0,0 +1,108 @@
|
||||
import 'reflect-metadata';
|
||||
import fs from 'fs';
|
||||
import path from 'path';
|
||||
import { parse } from 'csv-parse/sync';
|
||||
import { getDataSource } from '../lib/database';
|
||||
import { Customer } from '../lib/database/entities/Customer';
|
||||
|
||||
interface CustomerCSVRow {
|
||||
City: string;
|
||||
Name: string;
|
||||
'Website URL': string;
|
||||
Email: string;
|
||||
}
|
||||
|
||||
async function importCustomers(csvFilePath: string): Promise<void> {
|
||||
try {
|
||||
// Initialize database connection
|
||||
const dataSource = await getDataSource();
|
||||
const customerRepository = dataSource.getRepository(Customer);
|
||||
|
||||
// Read and parse CSV file
|
||||
const fileContent = fs.readFileSync(csvFilePath, 'utf-8');
|
||||
const records = parse(fileContent, {
|
||||
columns: true,
|
||||
skip_empty_lines: true,
|
||||
trim: true,
|
||||
}) as CustomerCSVRow[];
|
||||
|
||||
console.log(`Found ${records.length} records in CSV file`);
|
||||
|
||||
// Track processed emails to skip duplicates
|
||||
const processedEmails = new Set<string>();
|
||||
// Track existing names to ensure uniqueness
|
||||
const existingNames = new Set<string>(
|
||||
(await customerRepository.find()).map(customer => customer.name)
|
||||
);
|
||||
|
||||
let importedCount = 0;
|
||||
let skippedDuplicateEmail = 0;
|
||||
let skippedDuplicateName = 0;
|
||||
|
||||
for (const record of records) {
|
||||
const email = record.Email === 'null' ? '' : record.Email;
|
||||
const name = record.Name;
|
||||
|
||||
// Skip if email is already processed (not empty and already seen)
|
||||
if (email && processedEmails.has(email)) {
|
||||
console.log(`Skipping record with duplicate email: ${email}`);
|
||||
skippedDuplicateEmail++;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Skip if name already exists in database
|
||||
if (existingNames.has(name)) {
|
||||
console.log(`Skipping record with duplicate name: ${name}`);
|
||||
skippedDuplicateName++;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Add to processed sets
|
||||
if (email) {
|
||||
processedEmails.add(email);
|
||||
}
|
||||
existingNames.add(name);
|
||||
|
||||
// Create new customer
|
||||
const customer = new Customer();
|
||||
customer.name = name;
|
||||
customer.url = record['Website URL'] === 'null' ? '' : record['Website URL'];
|
||||
customer.email = email;
|
||||
|
||||
// Save to database
|
||||
await customerRepository.save(customer);
|
||||
importedCount++;
|
||||
|
||||
console.log(`Imported customer: ${name}`);
|
||||
}
|
||||
|
||||
console.log('Import summary:');
|
||||
console.log(`- Total records in CSV: ${records.length}`);
|
||||
console.log(`- Successfully imported: ${importedCount}`);
|
||||
console.log(`- Skipped (duplicate email): ${skippedDuplicateEmail}`);
|
||||
console.log(`- Skipped (duplicate name): ${skippedDuplicateName}`);
|
||||
|
||||
} catch (error) {
|
||||
console.error('Error importing customers:', error);
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
// Check if file path is provided as command line argument
|
||||
const csvFilePath = process.argv[2];
|
||||
if (!csvFilePath) {
|
||||
console.error('Please provide the path to the CSV file as a command line argument');
|
||||
console.error('Example: npm run import-customers -- ./data/customers.csv');
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
// Run the import function
|
||||
importCustomers(csvFilePath)
|
||||
.then(() => {
|
||||
console.log('Import completed successfully');
|
||||
process.exit(0);
|
||||
})
|
||||
.catch((error) => {
|
||||
console.error('Import failed:', error);
|
||||
process.exit(1);
|
||||
});
|
||||
Reference in New Issue
Block a user