So, I’m trying to create an extension for the UFM labels, to retrieve the “Name” of an Umbraco Commerce Entity. In this case a ‘country’.
I have a block-list where you select a country per block. I want the name of that country to show up in the blocklist. So I started with the UFM label: Country: {=country}. This works, but it returns the GUID of the country.
So I asked Claude Chat for assistance, and after a couple of tries I ended up with the following files:
umbraco-package.json
{
"name": "Commerce Country Name UFM",
"extensions": [
{
"type": "ufmComponent",
"alias": "My.Commerce.CountryName",
"name": "Commerce Country Name",
"api": "/App_Plugins/commerceCountryName/commerce-country-name.component.js",
"meta": {
"alias": "commerceCountryName"
}
},
{
"type": "bundle",
"alias": "My.Commerce.CountryName.Bundle",
"name": "Commerce Country Name Bundle",
"js": "/App_Plugins/commerceCountryName/commerce-country-name.element.js"
}
]
}
commerce-country-name.component.js
import { UmbUfmComponentBase } from '@umbraco-cms/backoffice/ufm';
import './commerce-country-name.element.js';
export class CommerceCountryNameApi extends UmbUfmComponentBase {
async render(token) {
const alias = token.text?.trim();
return `<commerce-country-name property-alias="${alias}"></commerce-country-name>`;
}
}
export { CommerceCountryNameApi as api };
commerce-country-name.element.js
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
import { html } from '@umbraco-cms/backoffice/external/lit';
import { UMB_BLOCK_ENTRY_CONTEXT } from '@umbraco-cms/backoffice/block';
class CommerceCountryNameElement extends UmbLitElement {
static properties = {
propertyAlias: { type: String, attribute: 'property-alias' },
_countryName: { type: String, state: true },
};
constructor() {
super();
this.propertyAlias = '';
this._countryName = '';
console.log('constructor hit');
}
async connectedCallback() {
console.log('callback');
super.connectedCallback();
// Haal de GUID op via de block entry context
this.consumeContext(UMB_BLOCK_ENTRY_CONTEXT, async (context) => {
if (!context) return;
const content = context.content;
const guid = content?.getValueByAlias(this.propertyAlias);
console.log('Country GUID:', guid);
if (guid) {
await this._fetchCountryName(guid);
}
});
}
async _fetchCountryName(guid) {
console.log('get');
try {
const response = await fetch(
`/umbraco/commerce/storefront/api/v1/country/${guid}`,
{ credentials: 'include' }
);
if (response.ok) {
const data = await response.json();
this._countryName = data.name ?? guid;
} else {
this._countryName = guid;
}
} catch {
this._countryName = guid;
}
}
render() {
return html`${this._countryName}`;
}
}
customElements.define('commerce-country-name', CommerceCountryNameElement);
The label in my blocklist now reads Country: [object Promise]
And I don’t see the console.log() lines I put in the Callback or Constructor.
I haven’t got any experience with extension development in U17 other than modifying a file here or there. So it might be something super simple. But I don’t know why the element’s constructor isn’t called. And Claude is comming up with solutions that only confuse me more, and don’t work either ![]()
Any help is appreciated!
