umbraco / Umbraco-CMS

Umbraco is a free and open source .NET content management system helping you deliver delightful digital experiences.
https://umbraco.com
MIT License
4.45k stars 2.68k forks source link

V8: Language Variants editable when language is not set in cultures & hostnames #4915

Closed jveer closed 3 years ago

jveer commented 5 years ago

It's currently possible to configure the language variants of a page even though the page is not available in that language.

Reproduction

Specifics

Steps to reproduce

  1. Clean install Umbraco 8
  2. Settings > Language > Add new. For example: German (Germany)
  3. Create a new document type, allow varying by culture. For example: Homepage
  4. Create a homepage in the content tree, named 'United Kingdom'
  5. Create another homepage in the content tree, named 'Germany'
  6. Right-click 'United Kingdom' > Cultures and hostnames...
  7. Add a domain with the English language
  8. Right-click 'Germany' > Cultures and hostnames...
  9. Add a domain with the German language
  10. Open the 'United Kingdom' homepage image

Expected result

I expect to be only able to change the English variant here, as this is the only culture I have configured.

Actual result

The actual result is that I am still able to configure (and publish) the German language in the United Kingdom homepage. image

image


_This item has been added to our backlog AB#4499_

kjac commented 5 years ago

First of all: Sounds like you should not be using culture variant document types to begin with, if you're going to create a separate content tree per language?

Anyway...

In a culture variant site it's very handy to be able to add content in all languages, even if the (final) domains aren't yet assigned to the root. I don't think we should be limiting the available languages in the editor based on the defined host names and their cultures. It'd only make it that much harder to get started, and ultimately add to the learning curve.

That being said you raise an interesting point (possible inadvertently): should we somehow be able to subset the available languages in the editor?

Consider an install with multiple sites, all of them culture variant. Is it given that I'd like all sites editable in all languages?

jveer commented 5 years ago

Thanks for your reply @kjac.

The reason we have separate culture variants is that we have region-specific sites with multiple languages. For the German website we would like to have all content available in German and English. In the end this setup will be used for about 20 countries with all different content and languages. We wouldn't want to have the content editor have a list of 20 languages when we only have two or three cultures that are being used on that region.

I do agree that linking the available languages to the cultures and hostnames may not be the right approach. It would however be nice to have available languages configurable in a similar way on the site root.

Thoughts?

kjac commented 5 years ago

My immediate thought is that the cultures assigned to the host names are exactly what would be needed for this case. A pretty perfect fit.

Maybe the core team can advise on an extension point that lets you filter out the available variant languages based on the root level domains?

kjac commented 5 years ago

After a bit more reflection... have a look at the SendingContentModel event on Umbraco.Web.Editors.EditorModelEventManager. If I'm not mistaken you can tweak the outgoing content using this event - e.g. filter out available variants.

If you succeed in your endeavour, by all means post the resulting code here for future reference. I have a feeling this isn't going to be an entirely uncommon case.

zpqrtbnk commented 5 years ago

Quick summary of what I understand:

Filtering the langs does not feel too uncommon indeed. Now, whether it should be done via hostnames... or done all the time... is a different question. I have the feeling that in some cases, we may want to see langs that would not be configured as hostnames. So... yes, ideally, there would be some sort of add-on code (using SendingContentModel?) event that could be used for this.

But then, when publishing, I assume the publish dialog would also need to ignore the ignored langs.

Someone needs to experiment with this.

kjac commented 5 years ago

@zpqrtbnk I don't think the publishing dialog would show the languages if they were filtered out in SendingContentModel - I'm almost sure all the save/publish/schedule/... dialogs simply iterate the available variants on the JS model on the client.

@jveer I don't suppose you had a chance to look at this yet?

jveer commented 5 years ago

@zpqrtbnk @kjac I'm currently having a look at this, the filtering on variants is possible on the SendingContentModel event. Just need a little more checks to make sure it also works when creating new content items. Will update you once finished!

jveer commented 5 years ago

Thanks both! Ended up using the following code, which seems to be working correctly. Any feedback is appreciated :)

private void EditorModelEventManager_SendingContentModel(HttpActionExecutedContext sender, EditorModelEventArgs<ContentItemDisplay> e)
{
    var contentId = e.Model.Id == 0 ? e.Model.ParentId : e.Model.Id;
    var contentDomains = new List<IDomain>();
    while (!contentDomains.Any() && contentId != -1)
    {
        var content = Current.Services.ContentService.GetById(contentId);
        if (content == null) break;

        contentId = content.ParentId;
        contentDomains = Current.Services.DomainService.GetAssignedDomains(content.Id, true).ToList();
    }

    if (contentDomains.Any())
    {
        var variants = e.Model.Variants.Where(variant => contentDomains.Any(domain => domain.LanguageIsoCode == variant.Language.IsoCode));
        e.Model.Variants = variants;
    }
}
kjac commented 5 years ago

@jveer nicely done, thanks for sharing!

Instead of fetching the parents one by one in the while loop you could probably use ContentService.GetAncestors(int id)... provided you also include an initial check for ParentId in case you're editing the current root (in which case ContentService.GetAncestors(int id) should return an empty list).

JeffreyPerplex commented 5 years ago

Hi all,

when adding new languages it can quite complex indeed. What we tried to achieve for one our clients (proof-of-concept with v8) is to create a website with seperate trees for four countries:

So my language collection looks like this:

2019-03-15 11_05_18-Window

The content trees are different per country, because the Dutch organization wants to have other pages on the firstlevel menu, and other stuff on the homepage than the other countries. Using the full multilingual options of v8 and make everything 1-on-1 translatable does not really make sense. So I've created the tree like this:

Contenttree

In this way every country has freedom about their content and tree structure.

I've assigned the correct domains to each country:

But as soon as I want to publish the homepage of a specifc country (let's say the Danish website) it says that I have mandatory languages specified and must(!) create a Dutch-variant and German (Switzerland)-variant before I can actually publish this page:

Mandatory languages

This does not really make sense of course and is not the way it was intended....

As a workaround I can remove the "mandatory" languages, but still a content editor would have the option to create language-variants for their website, but that does not make any sense.

My preferred solution

1) would be to only have the languages available that are assigned to the domain / rootnode are visible

2) the mandatory languages work, depending on whether they have been added to the domain. For Switzerland the German language is mandatory, but not the Dutch language...

Implementing this would only still cause some headaches when setting up the homepage / rootnode. At that moment ("Create new" => "Homepage" => "Publish" or "Save") no domains are assigned yet, so you cannot know which domains are relevant. A solution could that a domain has to be assigned at that moment (in the popup for example)....

Hope this comment helps a bit,

Jeffrey

kjac commented 5 years ago

@JeffreyPerplex I understand your position perfectly clear. I'm not at all against some kind of handling for this in Umbraco (although the mandatory language part can be a lot harder to solve than simply hiding some languages in the UI).

One could also argue that this is one of the "Make Umbraco simple to use and easy to customize" scenarios - meaning it shouldn't be handled out of the box but rather be easy to tweak, e.g. using EditorModelEventManager.

All in all it's a call that HQ needs to make. @zpqrtbnk can you carry this back to the table?

KevinJump commented 5 years ago

I would say this is more core then extra - I am with @JeffreyPerplex the editor shouldn't see language options for languages that are not relevant for that content, and you should be able to mix the 1-1 and tree-based approach to languages.

I have seen many multilingual sites and lots of them have this mix of single node 1-1 languages (for things like products) and then have separate sites for each language (for the sites) - it's fairly common (more often than not) I don't think the new multilingual features in v8 changes this model for many people.

there also needs to be some consideration of what happens when the number of languages gets large, a few people I have spoken with have 20+ or 40+ languages on their sites in v7. this dialog will just get to massive.

there was also an issue relating to permissions on language nodes: #3830 - this might aid in this situation.

jveer commented 4 years ago

Been some time since this ticket, @zpqrtbnk did you by any change be able to discuss this at HQ?

Also, for another project we ran in a similar issue (#7037) which is very much related to this ticket as this won't work without implementing different default languages.

nul800sebastiaan commented 4 years ago

Just as an update as I see some chatter around this:

  1. It is still possible (like in v7) to give each editor their own tree with their own language. Nothing has changed there.
  2. We're evaluating over time how people try to use the multilingual features in a single tree, including side-by-side editing etc. This is going to take some time and we don't yet have enough information to decide how what actions we're going to take.

We welcome discussion and feedback here, which will be how we determine the way forward.

umbrabot commented 3 years ago

Hiya @jveer,

Just wanted to let you know that we noticed that this issue got a bit stale and might not be relevant any more.

We will close this issue for now but we're happy to open it up again if you think it's still relevant (for example: it's a feature request that's not yet implemented, or it's a bug that's not yet been fixed).

To open it this issue up again, you can write @umbrabot still relevant in a new comment as the first line. It would be super helpful for us if on the next line you could let us know why you think it's still relevant.

For example:

@umbrabot still relevant This bug can still be reproduced in version x.y.z

This will reopen the issue in the next few hours.

Thanks, from your friendly Umbraco GitHub bot :robot: :slightly_smiling_face:

christianfredh commented 2 years ago

@umbrabot still relevant As far as I know, this has not been fixed in later versions and we have the exact same needs as described here: https://github.com/umbraco/Umbraco-CMS/issues/4915#issuecomment-473231232

Several site roots on same installation, each with different default language and available languages.