feat(migration): add skip rows option to CSV import
Allow users to skip the first N data rows when importing CSV files. This is useful when the CSV contains metadata rows before the actual task data begins. Adds skip_rows to ImportConfig (backend) and a number input in the parsing options UI (frontend).
This commit is contained in:
parent
e031a8d428
commit
56c4d97b50
|
|
@ -651,6 +651,7 @@
|
|||
"parsingOptions": "Parsing Options",
|
||||
"delimiter": "Delimiter",
|
||||
"dateFormat": "Date Format",
|
||||
"skipRows": "Skip Rows",
|
||||
"mapColumns": "Map Columns",
|
||||
"example": "e.g.",
|
||||
"preview": "Preview",
|
||||
|
|
|
|||
|
|
@ -46,6 +46,7 @@ export interface ImportConfig {
|
|||
delimiter: string
|
||||
quote_char: string
|
||||
date_format: string
|
||||
skip_rows: number
|
||||
mapping: ColumnMapping[]
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -83,6 +83,17 @@
|
|||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="option-group">
|
||||
<label for="skipRows">{{ $t('migrate.csv.skipRows') }}</label>
|
||||
<input
|
||||
id="skipRows"
|
||||
v-model.number="config.skip_rows"
|
||||
type="number"
|
||||
class="input"
|
||||
min="0"
|
||||
@change="updatePreview"
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
|
@ -240,6 +251,7 @@ const config = ref<ImportConfig>({
|
|||
delimiter: ',',
|
||||
quote_char: '"',
|
||||
date_format: '2006-01-02',
|
||||
skip_rows: 0,
|
||||
mapping: [],
|
||||
})
|
||||
|
||||
|
|
@ -314,6 +326,7 @@ async function handleFileUpload() {
|
|||
delimiter: result.delimiter,
|
||||
quote_char: result.quote_char,
|
||||
date_format: result.date_format,
|
||||
skip_rows: 0,
|
||||
mapping: result.suggested_mapping,
|
||||
}
|
||||
|
||||
|
|
@ -376,6 +389,7 @@ function resetToUpload() {
|
|||
delimiter: ',',
|
||||
quote_char: '"',
|
||||
date_format: '2006-01-02',
|
||||
skip_rows: 0,
|
||||
mapping: [],
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -126,6 +126,7 @@ type ImportConfig struct {
|
|||
Delimiter string `json:"delimiter"`
|
||||
QuoteChar string `json:"quote_char"`
|
||||
DateFormat string `json:"date_format"`
|
||||
SkipRows int `json:"skip_rows"`
|
||||
Mapping []ColumnMapping `json:"mapping"`
|
||||
}
|
||||
|
||||
|
|
@ -398,6 +399,11 @@ func PreviewImport(file io.ReaderAt, size int64, config ImportConfig) (*PreviewR
|
|||
return nil, &migration.ErrNotACSVFile{}
|
||||
}
|
||||
|
||||
// Skip rows if configured
|
||||
if config.SkipRows > 0 && config.SkipRows < len(rows) {
|
||||
rows = rows[config.SkipRows:]
|
||||
}
|
||||
|
||||
result := &PreviewResult{
|
||||
Tasks: make([]PreviewTask, 0, minInt(5, len(rows))),
|
||||
TotalRows: len(rows),
|
||||
|
|
@ -567,6 +573,11 @@ func MigrateWithConfig(u *user.User, file io.ReaderAt, size int64, config Import
|
|||
return &migration.ErrNotACSVFile{}
|
||||
}
|
||||
|
||||
// Skip rows if configured
|
||||
if config.SkipRows > 0 && config.SkipRows < len(rows) {
|
||||
rows = rows[config.SkipRows:]
|
||||
}
|
||||
|
||||
if len(rows) == 0 {
|
||||
return &migration.ErrFileIsEmpty{}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue