Europass import: a website or address already on the account under another kind or holder fails the whole import #616
Labels
No labels
accessibility
authentication
breaking change
bug
documentation
enhancement
interface
internationalisation
observability
performance
security
tier
1
tier
2
tier
3
tier/4
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
Postulo/postulo#616
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Found on 2026-09-29 in a read-only review of postulo at
95348908d, comparing what the Europass writer checks before inserting with the uniqueness constraints on the rows it writes, and settled by callingimporting.applyagainst such an account.Checked again on 2026-10-01 against
mainat0a5cad587: still present.importing.applywrites the file's website only after asking whether the profile has a website-kind link, and its address only after asking whether the profile has an address. The constraints it writes against are wider: aWebLinkis unique on its holder and URL whatever its kind, and aPostalAddressis unique on its owner and comparable form whatever it is attached to. A file that repeats either one raisesIntegrityErrorinside the view'stransaction.atomic(), the person gets a server error, and nothing of the import lands.resume/importing.py:141-145(web_links.primary_for(profile, web_links.Kind.WEBSITE) is None, thensave_only_link),core/web_links.py:227-241(save_only_linklooks for a hidden row withkind=kindonly), againstcore/models.py:677-680(web_link_unique_per_holderoncontent_type,object_id,url);resume/importing.py:95(_write_address:if postal.for_holder(profile).exists()), againstcore/models.py:564-568(address_unique_per_owneronowner,comparable); the transaction isresume/views.py:479-481.https://www.linkedin.com/in/leeas their social profile and has no website. Their Europass CV gives the same address as its website, as many do. Add all of this fails withUNIQUE constraint failed: core_weblink.content_type_id, core_weblink.object_id, core_weblink.url.UNIQUE constraint failed: core_postaladdress.owner_id, core_postaladdress.comparable.The parsed record stays in the session, so every retry fails the same way until the person finds and removes the row the import collides with, which nothing tells them.
resume/candidate.py:930-935,_same_address) and across the whole account (resume/candidate.py:870-899,comparable), so the two importers have drifted.importing.apply, skip the website when any link on the profile has the same address (compared ascandidate._same_addresscompares), and in_write_addressskip an address whosecomparable_form()the owner already holds anywhere. Record each skip inReport.skippedin words, so the rest of the import lands and the person knows what was left out. Sharing the comparison helpers between the two importers would stop them drifting again.Done when
tests/test_europass.pyimports, through the view, a file whose website is the account's existing social link and a file whose address is already on one of the owner's contacts; both answer with a redirect, the rest of the record is added, and the skip is reported.