Sitecore Glass Mapper always null - sitecore

I am using Sitecore Glass Mapper for a new project I'm setting up.
We are using Sitecore 7.2, latest version of Team Development for Sitecore (TDS) code generation and the latest version of glass.
The code I am trying to execute:
var b = new SitecoreContext();
var c = b.GetCurrentItem<T01_Homepage>();
b is not null. c is null.
var d = b.GetItem<T01_Homepage>("path")
d is null.
I added my assembly in GlassMapperScCustom:
public static IConfigurationLoader[] GlassLoaders(){
var attributes = new AttributeConfigurationLoader(new[] { "Company.Framework.Websites.Corporate", "Company.Framework.Core", "Company.Framework.Common" });
return new IConfigurationLoader[] { attributes };
}
When I look into b.GlassContext.TypeConfigurations all my models are there.
I figured it could be a language issue because the site is in dutch and maybe the wrong language would be resolved incorrectly. This was also not the case.
I disabled WebActivator and added the GlassMapperSc.Start() in my Global.asax Application_Start method.
We are also using Autofac as DI framework. But without it, it still isn't working as you can see above. Also when I create my own custom models without TDS code generation the result of GetCurrentItem<T> is null.
Does anyone have an idea how I can fix this?

Did you check your Sites.config and the default language for this website? There could be a difference between the language which is defined in your Sitecore languages folder and your configuration.
I had a similar problem with one of my projects where I changed the Sitecore.Context.Language to "nl" instead of "nl-NL". The glass mapper will return null, but Sitecore.Context.Database.GetItem will return an object in this case.

Most of the times it is a language issue. The mapper returns a null object when you do not have versions in the current or given language.
What can be confusing is that Sitecore.Context.Database.GetItem returns an object, even if it does not have a version in the current language. Be sure to check that item.Versions has any.

Some things you may try (this didn't fit in the comments field)
1) Confirm that the related fields in the Sitecore Item object contain values (so Sitecore.Context.Item for your "c" var and Sitecore.Context.Database.GetItem("path") for your "d" var)
2) Try to encapsulate the GetItem/GetCurrentItem call in a VersionCountDisabler, like this:
T01_Homepage model = null;
using (new VersionCountDisabler())
{
var context = new SitecoreContext();
model = context.GetItem<T01_Homepage>("path");
}
// Do you have data in model now?
3) Try to encapsulate the same call with a SecurityDisabler. Just to confirm it's not a security issue.
4) If you still don't know what it is, please update your question with some (simplified) code for your model.

Related

Entity Framework Core metadata is different than model and DB. How to refresh?

I'm new to using EF but it was relatively simple to implement for me, the problem came when I need to change the model. I created a column that I later deleted. However, at runtime the ghost column is causing an Invalid column error.
I have added this method to my context to confirm my suspicion.
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
bool destroy = false;
foreach (Microsoft.EntityFrameworkCore.Metadata.Internal.Property p in modelBuilder.Entity<File>().Metadata.GetProperties())
{
if (p.Name == "AppointmentID")
{
destroy = true;
}
}
}
I have tried to use framework core migration tools, adding and removing colums. That works great, but none of this gets rid of the reference to an old column.
Is there a way to reset this? It seems older versions of EF had physical files that were generated as the schemas/definitions of the columns. Is there something like that I could force to be refreshed?

Sitecore IsPageEditor and IsExperienceEditor

We are currently writing a module for Sitecore and have ran into a problem.
We have a pipeline in which we do the following check:
if (Sitecore.Context.PageMode.IsExperienceEditor)
{
return;
}
The problem is that one of our clients are running and older version of Sitecore (8.0 update 5) where the property IsExperienceEditor does not exist yet. See Sitecore release notes for next update where it is introduced.
To quickly fix the error we used the older deprecated property which is this:
if (Sitecore.Context.PageMode.IsPageEditor)
{
return;
}
Now the question is, is there any way in which we can test for the Sitecore version so we can have backwards compatibility in the module?
You can use the code which is executed in Sitecore in background of both properties mentioned by you:
if (Sitecore.Context.Site.DisplayMode == Sitecore.Sites.DisplayMode.Edit)
{
return;
}
I know that using Sitecore.Context.PageMode.IsExperienceEditor (or Sitecore.Context.PageMode.IsPageEditor) is more elegant, but in a situation when you need to support both old and new Sitecore versions, that's sounds like a good option.
The deprecated property of IsPageEditor is still present specifically for the purpose of backward compatibility. IsExperienceEditor is just a renamed property that does the same thing that IsPageEditor does.
However you can check for the existence of a property like this:
public static bool HasProperty(this object obj, string propertyName)
{
return obj.GetType().GetProperty(propertyName) != null;
}
Another option is to make two different versions of the module, if the implementation becomes significantly different for the different versions of Sitecore.

Sitecore: Glass Mapper Code First

It is possible to automatically generate Sitecore templates just coding models? I'm using Sitecore 8.0 and I saw Glass Mapper Code First approach but I cant find more information about that.
Not sure why there isn't much info about it, but you can definitely model/code first!. I do it alot using the attribute configuration approach like so:
[SitecoreType(true, "{generated guid}")]
public class ExampleModel
{
[SitecoreField("{generated guid}", SitecoreFieldType.SingleLineText)]
public virtual string Title { get; set; }
}
Now how this works. The SitecoreType 'true' value for the first parameter indicates it may be used for codefirst. There is a GlassCodeFirstDataprovider which has an Initialize method, executed in Sitecore's Initialize pipeline. This method will collect all configurations marked for codefirst and create it in the sql dataprovider. The sections and fields are stored in memory. It also takes inheritance into account (base templates).
I think you first need to uncomment some code in the GlassMapperScCustom class you get when you install the project via Nuget. The PostLoad method contains the few lines that execute the Initialize method of each CodeFirstDataprovider.
var dbs = global::Sitecore.Configuration.Factory.GetDatabases();
foreach (var db in dbs)
{
var provider = db.GetDataProviders().FirstOrDefault(x => x is GlassDataProvider) as GlassDataProvider;
if (provider != null)
{
using (new SecurityDisabler())
{
provider.Initialise(db);
}
}
}
Furthermore I would advise to use code first on development only. You can create packages or serialize the templates as usual and deploy them to other environment so you dont need the dataprovider (and potential risks) there.
You can. But it's not going to be Glass related.
Code first is exactly what Sitecore.PathFinder is looking to achieve. There's not a lot of info publicly available on this yet however.
Get started here: https://github.com/JakobChristensen/Sitecore.Pathfinder

How to programatically change TFS 2010 workitem link-type

I've used the tfs api to programatically add links between work items in different team-projects, currently all links are set as related links but I'd like to change some of them to some of the other types supported in tfs2010 e.g. "parent" etc. But I can't work out how to do it. Any ideas?
Edit:
Originally I added thus:
RelatedLink link = new RelatedLink(iLinkMe);
wi.Links.Add(link);
when I think I should have added:
WorkItemLinkTypeEnd linkTypEnd = store.WorkItemLinkTypes.LinkTypeEnds["Parent"];
RelatedLink linkBetter = new RelatedLink(linkTypEnd, iLinkMe);
wi.Links.Add(linkBetter );
but I didn't, (and I don't like the "Parent" string, I was looking for an enum), so how do I change the linkTypeEnd? I'm guessing I can modify this via wi.Links ?
Have a look at this site on how to Create Link Between Work Item (Parent, Child etc…).

How to programmatically update references in sitecore?

I have 2 templates: ArticleItem and ArticlePageItem, the ArticlePageItem has a ReferenceField 'Content.Reference' that links to an ArticleItem. Below is the code to create an article:
Item articlePageItem = articlePageParentItem.Add(articleItem.Name, new TemplateItem(master.GetItem(ConstantString.ArticlePageTemplateID)));
using (new UserSwitcher(Sitecore.Context.User))
{
articlePageItem.Editing.BeginEdit();
articlePageItem.Fields["Content.Reference"].Value = articleItem.ID.ToString();
articlePageItem.Editing.EndEdit();
}
But after I execute the code above, I cannot get the ArticleItem reference through Globals.LinkDatabase.GetReferences(articlePageItem), even though I use Globals.LinkDatabase.UpdateReference(articlePageItem).
Does anyone know how to implement this?
[Update]
Below is our environment:
We have a website based on Sitecore, and we're developing another system aims to simplify the article management. We use .NET 4 & ASP.NET MVC 3 to implement this system, and reference Sitecore.Kernal.dll & Sitecore.Client.dll to our project. But our sitecore version is 6.2 which is incomplatible with .NET 4, so I just copied part of the configurations. I think it maybe dues to the incomplete web.config.
If you are executing the above code you should also consider publishing the item changes.
This can be done by using the following code snippet:
// publish all changed content
Database webDatabase = Sitecore.Configuration.Factory.GetDatabase("web");
PublishOptions publishOptions = new PublishOptions(masterDatabase, webDatabase, PublishMode.Smart, Sitecore.Context.Language, DateTime.Now);
publishOptions.RootItem = vacatureRoot;
publishOptions.Deep = true;
Publisher publisher = new Publisher(publishOptions);
publisher.Publish();
Where 'vacatureRoot' is the root -> in your case articlePageParentItem
After publishing the references should be set automatically and should be retrievable by using the normal way of getting Fields.
It looks like you are using a ReferenceField and therefore your code should look something like this:
ReferenceField rfRef = Sitecore.Context.Item.Fields["Content.Reference"];
if(rfRef != null && rfRef.TargetItem != null)
{
//Your logic here
}
Answer for comment:
I think you could best use the following code fragment ->
Sitecore.Globals.LinkDatabase.UpdateReferences(articlePageItem);
I think this will do what the name says, update the references for this item.
Hope this will work for you!