---
title: "Upgrading from 2.3 to 3.0"
manual: "Academic Profiles"
version: "main"
permalink: "https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0@main"
source: "Upgrade/From23To30.rst"
rendered: "2026-10-15T10:24:29+00:00"
---

# Upgrading from 2.3 to 3.0 {#upgrade-from-2-3-to-3-0}

This page takes an installation of **academic_persons** 2.3 straight to
3.0, without the step to 2.4. Version 3.0 drops TYPO3 12, changes the shape of
the settings file and rebuilds the public detail view. From 2.4 it takes over
the content elements that stay hidden until a site includes the page TSconfig
of their components. The page leaves out the 2.4 states that 3.0 replaces:
version 1.x of **environment_state_manager**, see
[Important: New required dependency fgtclb/environment-state-manager](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-254-academic-persons@main), and the settings file in the shape
of 2.4, see [Feature: A validator flag that locks the frontend editor only](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-1790531591@main) and
[Important: Address postcode and street number accept text](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-841-academic-persons@main), which the page migrates once, to the
shape of 3.0. Work through the sections in order. Skip a step that does not
apply to the installation.

## Before you start {#upgrade-from-2-3-to-3-0-before-you-start}

Version 3.0 runs on TYPO3 13.4 from 13.4.35 on and on TYPO3 14.3 from 14.3.7
on, with PHP 8.2 or later.

**academic_persons** 3.0 needs these packages. Upgrade them first or in
the same deployment, in this order:

-   [`fgtclb/environment-state-manager`](https://packagist.org/packages/fgtclb/environment-state-manager) 2.x, new since 2.4, which this
    extension and **academic_base** 3.0 require. It is declared in
    `composer.json` as `^2.0.1` and in `ext_emconf.php` as
    `2.0.1-2.99.99`. Composer installs it on its own. A classic installation
    installs **environment_state_manager** 2.x before it activates
    **academic_base** 3.0 or this extension.
-   [`fgtclb/academic-base`](https://packagist.org/packages/fgtclb/academic-base) 3.0, the same release as this extension.

The extensions that require this one follow it in the same deployment, where
installed: **academic_persons_edit**,
**academic_contacts4pages** and **academic_persons_sync**.
Where **academic_persons_edit** is installed, its upgrade chapter is
due in the same deployment, because its editor is replaced and one of its
wizards repairs the profile images of this extension.

These changes have to ship in the same deployment as the update:

-   The contract rows the database update cannot convert are corrected first,
    see [Update the database](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-database@main).
-   A site without a site set includes the page TSconfig of the components, or
    the content elements are no longer offered, see
    [Make the content elements selectable](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-page-tsconfig@main).
-   Project code that extends a class, implements an interface or overrides a
    method of this extension whose signature changed follows it, or it fails
    with a fatal error, see [Adapt your code](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-code@main).

The module paths on this page are those of TYPO3 13, where the upgrade runs.

## Update TYPO3 first {#upgrade-from-2-3-to-3-0-typo3}

Update TYPO3 to 13.4.35 or later while the site still runs 2.3, which supports
TYPO3 13.4. Version 3.0 no longer installs on TYPO3 12, and Composer and the
Extension Manager refuse it next to an older patch release of TYPO3 13.

Stay on TYPO3 13 until the upgrade is complete. The content element wizard
`academicPersons_MigrateListTypeToCTypeContentElements` of this extension
reads the column `tt_content.list_type`, which TYPO3 14 removes, so it
only runs on TYPO3 13. The same holds for the content element wizards of
**academic_jobs**, **academic_persons_edit** and
**academic_projects** when the installation also has them. Move to
TYPO3 14.3.7 or later once they have run.

See [Breaking: Removed TYPO3 v12 support](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-removed-typo3-v12-support@main) and
[Important: TYPO3 13.4.35 or 14.3.7 is required](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-minimum-typo3-versions@main).

## Update the package {#upgrade-from-2-3-to-3-0-package}

```bash
composer require -W \
    'fgtclb/academic-base':'~3.0.0' \
    'fgtclb/academic-persons':'~3.0.0'
```

On a classic installation, install **environment_state_manager** 2.x
from the TER in **Admin Tools > Extensions** first, because neither
**academic_base** 3.0 nor this extension can be activated without it.
Then update **academic_base**, **academic_persons** and the
extensions that require it there, in this order. Run the commands of this page
with `typo3/sysext/core/bin/typo3` instead of `vendor/bin/typo3`.

```bash
vendor/bin/typo3 cache:flush
```

## Update the database {#upgrade-from-2-3-to-3-0-database}

Three of the changes cannot be applied to every database as it is. Check them
before the update:

-   The contract columns `organisational_unit`, `function_type` and
    `location` become `NOT NULL`. The change fails on PostgreSQL and
    on MySQL in strict mode while a row holds `NULL`, which a contract
    saved with an empty relation by 2.3 does. Update those rows to `0`
    first, [Important: Contract relation columns are NOT NULL now](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-1788195400@main) has the statements.
-   The year columns of the timeline entries become unsigned. Correct a
    negative year first, which nothing of the extension ever wrote. See
    [Important: The timeline year fields are constrained](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-profile-information-year-range@main).
-   The contract column `publish` is removed. Do not accept its removal
    yet, [The contract field "publish"](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-publish@main) decides whether its values are
    carried over first.

```bash
vendor/bin/typo3 extension:setup
```

Or apply the changes in **Admin Tools > Maintenance > Analyze
Database Structure**.

Versions 2.4 and 3.0 change these tables, and the comparison also applies the
changes of the index definitions TYPO3 13.4.35 and 14.3.7 bring:

-   The contract table gets the column
    `organisational_unit_sorting`, which an upgrade wizard of the next
    step fills.
-   The nine record tables of this extension are workspace aware now and get
    the columns `t3ver_oid`, `t3ver_wsid`, `t3ver_state` and
    `t3ver_stage` with an index. Until they exist, the backend record
    lists of the extension and the frontend rendering of a translated profile
    fail with a database error. On SQLite, check afterwards that the nine
    tables really carry the four columns, the command line path of TYPO3 adds
    only the index there. See
    [Breaking: Person records are workspace aware](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-person-records-are-workspace-aware@main).
-   `tx_academicpersons_domain_model_function_type` and
    `tx_academicpersons_domain_model_organisational_unit` get a
    `slug` column, which an upgrade wizard of the next step fills.
-   The three contract relation columns and the three year columns change as
    described above.
-   `tx_academicpersons_domain_model_address` gets an index on
    `import_identifier`, see [Feature: Import identifiers are shown, searchable and can be looked up](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-1790866812@main).

The analyzer offers `tx_academicpersons_domain_model_contract.publish`
for removal. It never drops a column on its own.

## Run the upgrade wizards {#upgrade-from-2-3-to-3-0-wizards}

Run the wizards in this order, after the database update, and on TYPO3 13:

1.  `academicPersons_MigrateListTypeToCTypeContentElements`,
    **Migrate "EXT:academic_persons" from list elements to content
    elements (list_type => CType)**, only if it is still offered.
1.  `academicPersons_seedContractOrganisationalUnitSorting`,
    **Seed the contract sort order of academic organisational units**.
1.  `academicPersons_fillFilterSlugs`, **Generate the URL segments
    of academic function types and organisational units**.
1.  `academicPersonsEdit_repairLocalizedProfileImages`,
    **Repair the profile image relations of academic profiles**, of
    **academic_persons_edit**, where that extension is installed.

```bash
vendor/bin/typo3 upgrade:run academicPersons_MigrateListTypeToCTypeContentElements
vendor/bin/typo3 upgrade:run academicPersons_seedContractOrganisationalUnitSorting
vendor/bin/typo3 upgrade:run academicPersons_fillFilterSlugs
```

A wizard that TYPO3 recorded as done is offered again once it is marked
undone. TYPO3 13 marks a wizard undone with
`vendor/bin/typo3 upgrade:mark:undone <identifier>`.
The two repeatable wizards of this step are never recorded as done.

`academicPersons_MigrateProfileAutoCreateExtensionsConfiguration` shipped
with 2.3 already. An installation that ran it there has nothing more to do.

### The content element wizard {#upgrade-from-2-3-to-3-0-ctype}

`academicPersons_MigrateListTypeToCTypeContentElements` shipped with 2.x
already and moves content elements stored as `list` with a
`list_type` of this extension onto their own `CType`. An
installation that ran it there has nothing more to do. TYPO3 14 no longer has
`tt_content.list_type`, so the wizard has to run on TYPO3 13, before the
core update. Run it by its identifier and not with a bare
`vendor/bin/typo3 upgrade:run`: the wizard is not repeatable, and a run
on TYPO3 14 that finds nothing records it as done although it migrated
nothing. Replace own TypoScript, TSconfig or SQL that matches on
`list_type` with a condition on `CType`. See
[Breaking: Extbase plugins require CType on TYPO3 v14](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-plugins-require-ctype-on-typo3-v14@main).

### The sort order of the organisational unit contracts {#upgrade-from-2-3-to-3-0-sorting}

A contract is an inline child of its profile and of its organisational unit, and
both relations wrote the same `sorting` column in 2.3, so saving an
organisational unit rearranged the contracts of every profile that owns one of
them. The unit relation has a column of its own now, which the database update
adds and the wizard **Seed the contract sort order of academic
organisational units**,
`academicPersons_seedContractOrganisationalUnitSorting`, fills with the order
the unit forms show today. Without it every contract carries `0` in the new
column until an editor saves its unit. Profiles keep ordering their contracts by
`sorting`, so the frontend is not affected either way. See
[Important: An organisational unit sorts its contracts on its own](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-organisational-unit-sorts-its-contracts@main).

**academic_partners** and **academic_contacts4pages** ship the
same repair for their own tables, as
`academicPartners_seedPartnershipRoleSorting` and
`academicContact4pages_seedContactSecondarySorting`. Run them in this step
where those extensions are installed.

### The URL segments of the filter records {#upgrade-from-2-3-to-3-0-filter-slugs}

The wizard **Generate the URL segments of academic function types and
organisational units**, `academicPersons_fillFilterSlugs`, is new in 3.0. It
gives every live function type and organisational unit without a slug the one
a backend save would generate from its name, and leaves a slug that is set
alone. The filters of the profile list read the slug, so a list filtered by a
function type reads `/persons/function/professor`, see
[Filtered lists](https://docs.typo3.org/permalink/fgtclb/academic-persons:configuration-route-enhancers-filters@main). Without it a filter keeps
working as a query argument. See [Feature: A filter form and speaking URLs for the visitor list](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-1791043401@main).

The wizard is repeatable. It is offered again whenever a record has no slug,
for example after an import of a project wrote one without it.

### The profile images of translations {#upgrade-from-2-3-to-3-0-profile-images}

The profile image is translatable now. A translation follows the image of the
default language until it gets an image of its own. The image relations that
**academic_persons_edit** wrote before 3.0 do not always fit that, and
its repeatable wizard `academicPersonsEdit_repairLocalizedProfileImages`
repairs them through the DataHandler, without deleting a file. Run it where
that extension is installed and profiles have images, before editors use the
new editor of a multilingual site. Its upgrade chapter describes the wizard.
See [Breaking: The profile image translates](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-profile-image-is-translatable@main).

Code that read the image of a translation through the record of the default
language resolves the reference of the translation now.

### The contract field "publish" {#upgrade-from-2-3-to-3-0-publish}

The contract toggle **Show this contract online?** is removed with its
column `publish`. No view of the extension has ever read it, so the
visibility of every contract stays as it is. See
[Breaking: The contract field "publish" has been removed](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-contract-publish-field-removed@main).

Only a project whose own code gave the flag a meaning, and left contracts out
that were not published, carries it over to the visibility of the contract.
The wizard `academicPersons_migrateContractPublishToHidden` does that, and it
ships unregistered, because on every other installation it would hide all
contracts. Register it in the [`Configuration/Services.yaml`](https://docs.typo3.org/m/typo3/reference-coreapi/main/en-us/ExtensionArchitecture/FileStructure/Configuration/ServicesYaml.html#file-extension-configuration-services-yaml) of the site
package, flush the caches, run it, flush the frontend caches, and remove the
registration again. [Important: The contract publish wizard has to be registered by hand](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-contract-publish-to-hidden-wizard@main) has the
registration and the order.

Then let the database analyzer drop the column. Once it is dropped, nothing can
be migrated any more.

## Adapt the configuration {#upgrade-from-2-3-to-3-0-configuration}

### The upgrade check {#upgrade-from-2-3-to-3-0-upgrade-check}

The console command `academic:upgrade:check` of **academic_base**
reads the stored configuration of the installation and reports what no longer
reaches the academic extensions. For this extension it reports a TypoScript
record or an import of a file that is gone, two fields of the settings that
write one column, and a site that still depends on the set
`fgtclb/academic-persons-default` or `fgtclb/academic-persons-standalone`,
which keep working as aliases of `fgtclb/academic-persons`. Run it on the
staging copy right after the package update, and again once the steps of this
section are done:

```bash
vendor/bin/typo3 academic:upgrade:check
```

With the extension key and a site it also finds the template overrides of the
site whose file is gone, and copies that are identical to the shipped file:

```bash
vendor/bin/typo3 academic:upgrade:check academic_persons --site=<site identifier>
```

Each finding, and what to do about it, is described in the [upgrade check](https://docs.typo3.org/p/fgtclb/academic-base/main/en-us/UpgradeCheck/Index.html)
of **academic_base**.

### Make the content elements selectable {#upgrade-from-2-3-to-3-0-page-tsconfig}

The site sets and static templates are cut per content element since 2.4, and
the six content elements are hidden for the whole installation until the page
TSconfig of their component brings them back. See
[Breaking: Site sets and static templates have been restructured](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-site-sets-and-static-templates-restructured@main) for the complete
change.

-   **Without a site set:** add
    **Academic Persons: All components (academic_persons)** in the page
    record of every site root, tab **Resources**, field
    **Include static Page TSconfig (from extensions)**, or the entries
    of the single content elements a site should offer, see
    [Include static page TSconfig](https://docs.typo3.org/permalink/fgtclb/academic-persons:static-pagetsconfig@main). This entry did not exist in 2.3. Without it the
    content elements are no longer offered in the backend.
-   **With a site set:** nothing to do. The sets
    `fgtclb/academic-persons-default` and `fgtclb/academic-persons-standalone`
    keep their names and deliver the page TSconfig of all six content elements.
    A site may name the aggregate `fgtclb/academic-persons` or single
    component sets instead.

Use one mechanism per site, never a site set and a static template together,
see [Do not combine both](https://docs.typo3.org/permalink/fgtclb/academic-persons:one-mechanism-per-site@main).

Until a component is included, an existing content element of it keeps
rendering and keeps its type: **academic_base** shows the stored type
in the field **Type** followed by
**(not enabled on this page)**, and saving keeps it. The warning of the
2.4 changelog entry that saving such a record rewrites its type describes the
state before a fix that **academic_base** 2.4 carries as well, see
[its changelog entry](https://docs.typo3.org/p/fgtclb/academic-base/main/en-us/Changelog/2.4/Important-HiddenContentTypeStaysSelectable.html).
A content element that a page TSconfig of your own already turned into another
type is not repaired. Correct it by hand from its record history.

The **Person Contact Card** offers the field **Detail Page**,
which the page TSconfig of 2.3 disabled. To keep it hidden, see
[Important: The profile card offers the detail page](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-833-academic-persons@main).

### Static templates and imports {#upgrade-from-2-3-to-3-0-static-templates}

A `sys_template` record keeps working without a change. Both values its
field **Include TypoScript sets** on the tab **Advanced
Options** can store, `EXT:academic_persons/Configuration/TypoScript/Default` and
`EXT:academic_persons/Configuration/TypoScript/Standalone`, still resolve.
Only their labels changed, to **Academic Persons: Shared plugin
settings** and **Academic Persons: Standalone page**.

An `@import` of a shipped file in a site package has to be checked.
These files were removed:

-   [`Configuration/TypoScript/constants.typoscript`](https://docs.typo3.org/m/typo3/reference-coreapi/main/en-us/ExtensionArchitecture/FileStructure/Configuration/TypoScript/Index.html#file-extension-configuration-typoscriptconstants-typoscript) and
    [`Configuration/TypoScript/setup.typoscript`](https://docs.typo3.org/m/typo3/reference-coreapi/main/en-us/ExtensionArchitecture/FileStructure/Configuration/TypoScript/Index.html#file-extension-configuration-typoscriptsetup-typoscript), the deprecated forwards
    to `Configuration/TypoScript/Default/`,
-   [`Configuration/TypoScript/Standalone/constants.typoscript`](https://docs.typo3.org/m/typo3/reference-coreapi/main/en-us/ExtensionArchitecture/FileStructure/Configuration/TypoScript/Index.html#file-extension-configuration-typoscriptconstants-typoscript) and
    [`Configuration/TypoScript/Standalone/setup.typoscript`](https://docs.typo3.org/m/typo3/reference-coreapi/main/en-us/ExtensionArchitecture/FileStructure/Configuration/TypoScript/Index.html#file-extension-configuration-typoscriptsetup-typoscript),
-   `Configuration/TSconfig/page.tsconfig`, now
    `Configuration/TSconfig/Full/page.tsconfig`,
-   the files below `Configuration/Sets/AcademicPersonsDefault/` and
    `Configuration/Sets/AcademicPersonsStandalone/`.

An `@import` of a missing file fails silently and shows up as
missing configuration. The breaking change entry linked above has the table of
old and new paths.

### Grouping and sorting of the profile list {#upgrade-from-2-3-to-3-0-grouping-and-sorting}

The defaults of `plugin.tx_academicpersons.demand.groupBy` and
`plugin.tx_academicpersons.demand.sortBy` are the same with and
without a site set now, `lastNameAlpha` and `lastName`.

-   A site without a site set now groups a profile list by the first letter of
    the last name unless it sets `demand.groupBy` itself. Set the
    constant to an empty value to keep an ungrouped list.
-   A site on a site set now sorts a profile list by last name unless it sets
    `demand.sortBy` itself. The value `title` the sets shipped up
    to 2.3 was rejected by the extension, so these lists had no ordering at
    all.

### The settings file {#upgrade-from-2-3-to-3-0-settings}

A site package that ships its own
`Configuration/AcademicPersons/Settings.yaml` has to be migrated. The
file is built from four maps now, `profile`, `special`,
`contracts` and `documentSections`, and the top-level keys
`validations` and `profileInformationsTypes` of 2.3 are gone. See
[Breaking: Section-based AcademicPersons settings](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-section-based-academic-persons-settings@main).

A file that still ships the old keys keeps working for now. They are mapped
onto the new maps at runtime, with a warning in the log, until version 4.0.
The migration command prints the maps that replace them:

```bash
vendor/bin/typo3 academic:persons:settings:migrate
```

It never writes the file, and it exits with `1` while a package ships an old
key. Paste the printed maps into the site package in place of the old keys,
review them and flush all caches. Read the notes the command prints: a changed
`type` or `fieldName` of a timeline type is not applied, a
timeline type of a project needs its own column in a TCA override of the
profile table. See [Feature: Legacy settings overlay and migration command](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-legacy-settings-overlay-and-migration-command@main)
and [Migrating a pre-3.0 override](https://docs.typo3.org/permalink/fgtclb/academic-persons:configuration-validations-migration@main).

The settings files are merged recursively now. A key the override leaves out
is inherited from **academic_persons**, at every level, where leaving
it out removed it before. An entry that is to be gone is set to `~`, a
flag list that is to be empty to `[]`. Compare the override with the
shipped file key by key, `--delta` prints the keys a copied map leaves out:

```bash
vendor/bin/typo3 academic:persons:settings:migrate --delta
```

See [Breaking: Settings files merge recursively](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-settings-files-merge-recursively@main) and
[Feature: Settings overrides are reported and shrunk](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-settings-override-report-and-delta@main).

The shipped defaults changed as well: the gender of a profile and the start
date of a contract are required, the website, the publications link and the
links of the timeline entries carry the `url` flag, the type of an email
address or a phone number is no longer required, and the postcode and the
street number of an address lose the `number` flag, so they are stored
as entered. Change them in the override where the installation wants the old
behaviour, [Profile sections](https://docs.typo3.org/permalink/fgtclb/academic-persons:configuration-sections@main) documents every key.

### TCA overrides of the person tables {#upgrade-from-2-3-to-3-0-tca-overrides}

The settings set `required` and `readOnly` of a column after every TCA
override of a site package now, not before. A site package that sets either of
them on a configured column in `Configuration/TCA/Overrides` loses that
value. Move the lock or the requirement into the settings file. See
[Breaking: Settings apply after the TCA overrides](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-settings-apply-after-tca-overrides@main).

A site package that names a FlexForm data structure of this extension by path
checks the path. `Core12/` is gone, `SelectedProfiles.xml` and
`SelectedContracts.xml` are directly in
`Configuration/FlexForms/` now, `List.xml` and `Detail.xml`
have a `Core13/` and a `Core14/` variant. See
[Important: FlexForm paths change for the plugin structures](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-plugin-flexforms-are-split-per-core-version@main).

### Extension configuration {#upgrade-from-2-3-to-3-0-extension-configuration}

Two options are new, `profile.feuser.telephoneNumberType` and
`profile.feuser.faxNumberType`. They decide which phone number type
the telephone and fax numbers of a frontend user are imported as, and default
to `business`. The next synchronization run writes `business` where an
imported record still carries the type `phone` or `fax` and the installation
does not offer it. Set the options in **Admin Tools > Settings >
Extension Configuration** to type the imported numbers differently. See
[Feature: Configurable frontend user phone number types](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-configurable-frontend-user-phone-number-types@main).

Check the lists `demand.allowedSortByValues`,
`demand.allowedGroupByValues`, `types.emailAddressTypes`,
`types.phoneNumberTypes` and `types.physicalAddressTypes` for an entry
without a value, such as `=Private`. Such an entry is ignored now, and a record
stored with it shows its type as an invalid value in the backend until it is
saved with another one. See [Important: Empty configured values are ignored](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-438-academic-persons@main).

### Routing {#upgrade-from-2-3-to-3-0-routing}

A site configuration that imports more than one of the route enhancer files
`List.yaml`, `ListAndDetail.yaml` and `Detail.yaml` has to
limit each enhancer to the pages that carry its plugin with
`limitToPages`. Otherwise the enhancer imported first takes the URLs of
the others, and the detail page answers `404`. See
[Important: Route enhancers have to be limited to their pages](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-route-enhancers-limit-to-pages@main) and
[Route enhancers](https://docs.typo3.org/permalink/fgtclb/academic-persons:configuration-route-enhancers@main).

### Labels {#upgrade-from-2-3-to-3-0-labels}

-   A frontend label override under
    `plugin.tx_academic_persons._LOCAL_LANG` no longer has an
    effect. Move it to `plugin.tx_academicpersons._LOCAL_LANG`, or
    to the path of the one plugin it is meant for. See
    [Important: Label overrides are read from the documented path](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-label-overrides-use-the-documented-path@main) and
    [Labels](https://docs.typo3.org/permalink/fgtclb/academic-persons:configuration-labels@main).
-   The backend labels of the relation between frontend users and profiles
    moved from **academic_persons_edit** into this extension, to
    `EXT:academic_persons/Resources/Private/Language/locallang_tca.xlf`.
    An override through
    `$GLOBALS['TYPO3_CONF_VARS']['SYS']['locallangXMLOverride']` has to
    target the new file. The tab of the profile form is keyed
    `tx_academicpersons_domain_model_profile.div.frontend_users.label`
    there. See [Important: Frontend user labels moved into this extension](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-frontend-user-labels-moved@main).
-   A further translation of `locallang.xlf` renames the unit
    `contracts.emailAdresses` to `contracts.emailAddresses`, see
    [Important: The contract e-mail label shows in English](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-contract-email-label-unit-id@main), and takes over the units
    the detail view adds, `detail.subline`, `detail.contact` and
    `detail.navigation`, see [Important: Label changes of the public profile](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-public-profile-label-changes@main).

### Profile synchronization {#upgrade-from-2-3-to-3-0-profile-synchronization}

`academic:createprofiles` and `academic:updateprofiles` process
hidden profiles and disabled frontend users as well now, and ignore the start
and end time of profiles and frontend users and the frontend user groups of
profiles. They update the data of such a profile and leave its visibility
alone. A profile that was kept out of the synchronization by hiding it, or by
disabling its frontend user, is overwritten by the next run.

Before the first run, set **Disable profile sync** (`skip_sync`)
on every profile that must not be synchronized. See
[Breaking: Profile synchronization now includes hidden profiles and users](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-1782285582@main) and [Important: Profile synchronization ignores the visibility window](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-667-academic-persons@main).

`academic:createprofiles` also creates a profile for a disabled frontend
user, and for one outside its start and end time, that has none yet. Exclude
the page of such frontend users with `--exclude-pids`, or delete the
profiles created for them.

Both commands refuse a value of `--include-pids` or
`--exclude-pids` with a part that is not a page uid, and exit with code
`2`. Check the arguments of scheduler tasks and scripts. See
[Important: Profile create and update commands refuse wrong page lists](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-845-academic-persons@main).

`academic:updateprofiles` stores new records next to their profile or
contract instead of on the page of the frontend user. Moving the records an
earlier run stored there is optional, [Important: Updated profiles keep new records on their page](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-843-academic-persons@main)
has the queries that find them.

## Adapt templates and assets {#upgrade-from-2-3-to-3-0-templates}

An override keeps its own copy and does not receive a change of the shipped
file. The upgrade check with the extension key and a site finds overrides of
files that are gone, and copies that are identical to the shipped file, see
[The upgrade check](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-upgrade-check@main). Compare every other override with
the shipped file of 3.0 and take the changes over. [Overriding templates](https://docs.typo3.org/permalink/fgtclb/academic-persons:templates-override@main)
describes how the overrides are set up. Every template translates its labels
with the extension name `AcademicPersons` now, which moves the path of a
label override, see [Labels](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-labels@main). The paths below are
relative to `Resources/Private/`:

| File | What changed | Entry |
| --- | --- | --- |
| `Templates/Profile/Detail.html` | Rewritten. It dispatches the configured elements to the partials below `Partials/Profile/PublicProfile/`. An override keeps rendering its own copy and loses the configurable layout. | [Feature: Configurable public profile](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-configurable-public-profile@main) |
| `Partials/Profile/DataHeader.html` | Deleted. A template that still renders it fails at render time. `Partials/Profile/Header.html` and `Partials/Profile/SectionHeader.html` are no longer rendered by the detail view. | [Breaking: The partials of the detail view change](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-public-profile-detail-partials@main) |
| `Partials/Profile/Header.html`, `Partials/Profile/SectionHeader.html` | Take the class of the heading as the argument `class` in place of `positionClass`. | [Breaking: Header partials take a class argument](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-persons-header-partials-take-a-class-argument@main) |
| `Partials/Profile/Item.html`, `Partials/Profile/List/ItemList.html` | Built from small partials below `Partials/Profile/Item/` and `Partials/Profile/List/`. A copy of the two files does not reach the small ones, and a copy of the contract partial reads `detailLink` in place of `detailUri`. The name leaves out empty parts. | [Important: The profile item and list are built from partials](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-profile-item-and-list-partials@main), [Important: Profile names leave out empty parts](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-853-academic-persons@main) |
| `Partials/Profile/Contract/Field.html` | Renders the organisational unit and the title of the location, a `tel:` target without spaces, and the office hours as HTML. | [Important: Contract rows render the location, the unit and dialable phones](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-contract-fields-render-the-unit-and-tel-targets@main), [Important: List items render office hours as HTML](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-contract-field-office-hours-render-as-html@main) |
| `Partials/Profile/List/AlphabetPagination.html`, `Templates/Profile/List.html` | Letters without profiles are disabled, and a list with a manual selection renders no letter navigation. | [Important: Letters without profiles are disabled in the letter navigation](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-letter-navigation-markup@main), [Important: No letter navigation for a manual selection](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-no-letter-navigation-for-a-manual-selection@main) |

### The profile image {#upgrade-from-2-3-to-3-0-images}

The profile card and the detail view render the image as a
`<picture>` through the image partial of **academic_base**, and
a card of a profile without an image shows a placeholder. Adjust CSS that
selected the image as a direct child. Set
`plugin.tx_academicpersons.image.placeholder.default` to an empty
value to keep such cards without an image. A view whose partial root paths are
replaced as a whole adds
`-1 = EXT:academic_base/Resources/Private/Partials/`. See
[Breaking: Profile images render as a responsive picture](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-profile-images-render-as-picture@main) and
[Profile image](https://docs.typo3.org/permalink/fgtclb/academic-persons:templates-profile-image@main).

### Classes and styles {#upgrade-from-2-3-to-3-0-classes}

The templates carry the speaking `ace-*` classes the academic extensions
share, in place of the classes of the Bootstrap card, the list group and the
pagination. Only the grid classes, the button classes and
`visually-hidden` of Bootstrap stay. Move the selectors of the site
stylesheet to the new classes, the chapter [Styling](https://docs.typo3.org/permalink/fgtclb/academic-persons:styling@main) shows the
markup of every view. See [Breaking: Profile templates carry speaking classes](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-persons-speaking-frontend-classes@main).

The extension ships no stylesheet, as in 2.3. Only the development versions
of 3.0 shipped one for the profile views. The detail view needs two rules of
the site to work: one that hides the expand or the collapse glyph of a
fold-out entry by its `aria-expanded` state, and one that makes the
navigation of the left column sticky. The stylesheet of the development
instances is an example, see [An example](https://docs.typo3.org/permalink/fgtclb/academic-persons:styling-example@main) and
[Breaking: The profile views ship no stylesheet](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-public-profile-ships-no-stylesheet@main).

The detail view loads the module
`@fgtclb/academic-persons/frontend/profile.js`. A site that brings a script
of its own switches it off with
`plugin.tx_academicpersons.assets.js`, see
[Feature: The script of the public profile can be switched off](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-1791566503@main).

### Icons {#upgrade-from-2-3-to-3-0-icons}

Every icon of this extension is renamed, without an alias. The record icons are
`tx-academicpersons-record-*` now, the content element icon `persons_icon`
has three successors `tx-academicpersons-plugin-*`, and the icon files of 2.3
below `Resources/Public/Icons/` are deleted. An old identifier renders
TYPO3's `default-not-found` placeholder. Replace the identifiers in templates,
TSconfig, TCA, PHP and CSS of the site package, and move a replacement icon to
the new identifier. See
[Breaking: Renamed icons and a frontend icon registry](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-persons-public-profile-icons-moved-to-the-frontend-icon-registry@main).

## Adapt your code {#upgrade-from-2-3-to-3-0-code}

-   The two `itemsProcFunc` classes moved to the namespace
    `\FGTCLB\AcademicPersons\Backend\FormEngine`, as `ContractItems`
    and `ProfileShowFieldsItems`, and the method of the latter is
    `itemsProcFunc()` now. Own TCA or FlexForm configuration, and a class
    that extends one of them, uses the new names. See
    [Breaking: Renamed itemsProcFunc handler classes to FormEngine namespace](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-1783613367@main).
-   The list, detail, selected profiles and selected contracts plugins no
    longer dispatch `ModifyListProfilesEvent`,
    `ModifyDetailProfileEvent`, `ModifySelectedProfilesEvent` and
    `ModifySelectedContractsEvent`, and the classes are removed. A
    listener of one of them is never called again, without an error. Search
    the project code for the four class names. A listener that assigns view
    variables moves to `ModifyPluginViewEvent` of
    **academic_base**, a change of the demand to
    `ModifyProfileDemandEvent`. See
    [Breaking: The list, detail and selection events of the plugins are gone](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-removed-profile-view-events@main) and
    [ModifyPluginViewEvent](https://docs.typo3.org/permalink/fgtclb/academic-persons:developers-event-modify-plugin-view-event@main).
-   A project that extends or replaces `ProfileDemand`,
    `ProfileRepository`, `ContractRepository` or
    `ProfileController` takes the parameters and the demand flag of 2.4
    into account, see [Important: Extended ProfileDemand, findByUids() and demand handling](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-ace-250-academic-persons@main). An override of
    `ProfileRepository::findByDemand()` in a subclass or an XCLASS is a
    fatal error until it takes the new trailing context parameter of 3.0. An
    override of either `findByUids()` keeps loading and is no longer
    called by the selected profiles and selected contracts plugins. Move both
    to a listener of the query events. See
    [Breaking: The plugins call different repository finders](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-profile-and-contract-finder-signatures@main) and
    [Narrowing what a plugin shows](https://docs.typo3.org/permalink/fgtclb/academic-persons:developers-query-events@main).
-   A class of a project that implements
    `\FGTCLB\AcademicPersons\Domain\Model\Dto\PluginControllerActionContextInterface`
    adds `getContentObjectRenderer()`, or is a fatal error. See
    [Breaking: The persons plugin action context extends the one of academic_base](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-plugin-controller-action-context-interface-extends-base@main).
    The interface and its class are deprecated and removed in 4.0. Type new
    code against the interface of **academic_base**, see
    [Deprecation: The plugin action context of academic_persons](https://docs.typo3.org/permalink/fgtclb/academic-persons:deprecation-persons-plugin-controller-action-context@main).
-   A project that extends or replaces the models `Address`, `Email`
    or `PhoneNumber` adds the `hidden` property with its getter and
    setter. See [Feature: Visibility (hidden) support for contact record models](https://docs.typo3.org/permalink/fgtclb/academic-persons:feature-1782285578@main).
-   `SynchronizerContext` moved from the namespace
    `\Dto\Syncronizer` to `\Dto\Synchronizer`, and its property and
    named argument lost the same misspelling. See
    [Breaking: The synchronizer context namespace is fixed](https://docs.typo3.org/permalink/fgtclb/academic-persons:breaking-synchronizer-context-namespace-corrected@main).
-   A DataHandler hook of the project that dispatched
    `AfterProfileUpdateEvent` after a backend save is removed. The
    extension announces a backend save itself now, and the hook would announce
    it a second time. See
    [Important: Backend saves announce profile updates](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-backend-saves-announce-profile-updates@main).
-   Code outside this extension that looks up imported telephone records by
    the import identifier `phone:fe_users:<uid>` uses
    `telephone:fe_users:<uid>` now. See
    [Important: Imported telephone records use a stable identifier](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-imported-telephone-records-use-a-stable-identifier@main).
-   Code that calls `setPublish()`, `isPublish()` or
    `getPublish()` of a contract, or reads or writes `publish`, uses
    the visibility of the contract, see
    [The contract field "publish"](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-publish@main).
-   A query of the project with its own `QueryBuilder` on one of the nine
    tables sees workspace versions as rows now. Add the workspace restriction
    and the version overlay, as the entry linked in
    [Update the database](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-database@main) shows.
-   Code that uses `Validation`, `ValidationSet` or the
    `validationEnsure` ViewHelper of this extension imports them from
    **academic_base**, where they moved without an alias. See
    [Important: Validation primitives moved to EXT:academic_base](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-validation-primitives-moved-to-academic-base@main).

## Check the result {#upgrade-from-2-3-to-3-0-check}

-   The upgrade check exits with `0`, without and with the extension
    key, see [The upgrade check](https://docs.typo3.org/permalink/fgtclb/academic-persons:upgrade-from-2-3-to-3-0-upgrade-check@main).
-   `vendor/bin/typo3 academic:persons:settings:migrate` exits with
    `0`, and the log carries no warning about legacy settings.
-   The new content element wizard offers the content elements on the pages of
    every site that should have them, under the titles of 3.0, see
    [Important: Content elements have new titles and descriptions](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-content-element-titles-and-descriptions@main), and an existing
    persons content element opens in the backend with its own type.
-   The backend record lists of the extension open, and a translated profile
    renders in the frontend.
-   A profile list groups and sorts its profiles as intended, and a list
    filtered by a function type or an organisational unit shows the slug in
    the URL.
-   An organisational unit form lists its contracts in the order it showed
    before the update.
-   The detail page is hidden in menus. A request of it without a profile ends
    with the "page not found" handling of the site, see
    [Important: The profile detail answers "not found" without a profile](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-profile-detail-answers-not-found-without-a-profile@main).
-   Where organisational units are translated, no contract shows twice on a
    profile.
    [Important: Localizing an organisational unit leaves contracts alone](https://docs.typo3.org/permalink/fgtclb/academic-persons:important-localizing-an-organisational-unit-keeps-its-contracts@main)
    has the query that lists the contracts an earlier localization created.
-   A translated profile shows an image in every language, and a timeline
    entry shows its year in the frontend and in the backend form.
-   The detail view folds its entries in and out, and the site stylesheet
    reaches the lists, the card and the detail view.
-   A run of `academic:updateprofiles` exits with `0`, and a
    profile with **Disable profile sync** set stays unchanged.
