Fournisseur de cartes de site MVC et localisation

J’ai découvert aujourd’hui que pour mon site, je pourrais utiliser un fournisseur SiteMap que j’ai téléchargé de Github pour le MVC3, car mon application Web s’appelle MVC3.

La situation suit, mon application est multilingue. J’ai une bibliothèque séparée qui contient toutes les ressources. Cette bibliothèque est ensuite ajoutée à mon projet actuel et partout où j’ai besoin d’utiliser ces fichiers de ressources.

Maintenant, j’ai implémenté le fournisseur de plan de site:

     

Mais quand je le lance, j’obtiens une erreur car il ne trouve pas la ressource avec la clé home. Je pense que cela est dû au fait qu’il se trouve en dehors de l’application mais dans une bibliothèque séparée.

Comment puis-je pointer sur le fichier de ressources alors, qui est situé din projet distinct?

L’approche que j’adopterais serait de basculer vers une ID externe, puis d’implémenter une classe ISsortingngLocalizer personnalisée capable de lire les ressources d’un autre assemblage. Voici un exemple de travail. J’ai également créé une application de démonstration sur GitHub.

 using System; using System.Collections.Specialized; using System.Resources; namespace MvcSiteMapProvider.Globalization { public class ResourceManagerSsortingngLocalizer : ISsortingngLocalizer { public ResourceManagerSsortingngLocalizer( ResourceManager resourceManager ) { if (resourceManager == null) throw new ArgumentNullException("resourceManager"); this.resourceManager = resourceManager; } protected readonly ResourceManager resourceManager; ///  /// Gets the localized text for the supplied atsortingbuteName. ///  /// The name of the atsortingbute (as if it were in the original XML file). /// The current object's value of the atsortingbute. /// True if localization has been enabled, otherwise false. /// The resource key from the ISiteMap class. /// The implicit resource key. /// A  containing the explicit resource keys. ///  public virtual ssortingng GetResourceSsortingng(ssortingng atsortingbuteName, ssortingng value, bool enableLocalization, ssortingng classKey, ssortingng implicitResourceKey, NameValueCollection explicitResourceKeys) { if (atsortingbuteName == null) { throw new ArgumentNullException("atsortingbuteName"); } if (enableLocalization) { ssortingng result = ssortingng.Empty; if (explicitResourceKeys != null) { ssortingng[] values = explicitResourceKeys.GetValues(atsortingbuteName); if ((values == null) || (values.Length <= 1)) { result = value; } else if (this.resourceManager.BaseName.Equals(values[0])) { try { result = this.resourceManager.GetString(values[1]); } catch (MissingManifestResourceException) { if (!string.IsNullOrEmpty(value)) { result = value; } } } } if (!string.IsNullOrEmpty(result)) { return result; } } if (!string.IsNullOrEmpty(value)) { return value; } return string.Empty; } } } 

Ensuite, vous pouvez l'injecter dans votre module de configuration DI (exemple de StructureMap illustré, mais tout conteneur DI fera l'affaire).

Tout d'abord, vous devez spécifier de ne pas enregistrer l'interface ISsortingngLocalizer automatiquement en l'ajoutant à la variable excludeTypes.

 var excludeTypes = new Type[] { // Use this array to add types you wish to explicitly exclude from convention-based // auto-registration. By default all types that either match I[TypeName] = [TypeName] or // I[TypeName] = [TypeName]Adapter will be automatically wired up as long as they don't // have the [ExcludeFromAutoRegistrationAtsortingbute]. // // If you want to override a type that follows the convention, you should add the name // of either the implementation name or the interface that it inherits to this list and // add your manual registration code below. This will prevent duplicate registrations // of the types from occurring. // Example: // typeof(SiteMap), // typeof(SiteMapNodeVisibilityProviderStrategy) typeof(ISsortingngLocalizer) }; 

Ensuite, fournissez un enregistrement explicite du ResourceManagerSsortingngLocalizer (et de ses dépendances) à la place.

 // Configure localization // Fully qualified namespace.resourcefile (.resx) name without the extension ssortingng resourceBaseName = "SomeAssembly.Resources.Resource1"; // A reference to the assembly where your resources reside. Assembly resourceAssembly = typeof(SomeAssembly.Class1).Assembly; // Register the ResourceManager (note that this is application wide - if you are // using ResourceManager in your DI setup already you may need to use a named // instance or SmartInstance to specify a specific object to inject) this.For().Use(() => new ResourceManager(resourceBaseName, resourceAssembly)); // Register the ResourceManagerSsortingngLocalizer (uses the ResourceManger) this.For().Use(); 

Ensuite, il suffit de spécifier les ressources de manière appropriée. Vous devez les démarrer avec le nom de base (dans ce cas, SomeAssembly.Resources.Resource1 ), puis spécifiez la clé de la ressource comme deuxième argument.

  

Notez que l’obtention du nom de base correct est la clé pour que cela fonctionne. Consultez la documentation MSDN suivante: http://msdn.microsoft.com/en-us/library/yfsz7ac5(v=vs.110).aspx

Je pense que ça devrait être comme ça:

En supposant que votre:

NomProjet = MonProjet

Dossier contenant des ressources: LanguageFiles

Classe dans laquelle les ressources sont définies: Messagerie

puis.

Cela devrait être comme ça, je crois. Je ne suis pas sûr, mais peut-être que cela fonctionne pour vous:

 `[email protected]' 

(en supposant que Home est la ressource définie dans la classe Messaging)