Manully creating content part

Topics: Customizing Orchard, Writing modules
Apr 22, 2011 at 5:15 PM
Edited Apr 22, 2011 at 5:16 PM

I am trying to manually add a part via code and display it via a driver.  I have been able to save a part to the db via code now I wont to display the info via the driver and I am having no luck.

Creation Code

 

      var myPart = _services.ContentManager.New<CoursePart>("MyType");
      myPart.ActivityID = 1;
      myPart.Number = "MyNumber";
      myPart.Season = "MySeason";
      myPart.Year = "2011";
      myPart.Title = "MyTitle";
      _services.ContentManager.Create(myPart);
 

 

Driver Code

 

    protected override DriverResult Display(CoursePart part, string displayType, dynamic shapeHelper)
    {
      return ContentShape("Parts_Course",
          () => shapeHelper.Parts_Course(
              ActivityID: part.ActivityID,
              Title: part.Title));
    }
 

 

part has no info when getting into the display function;

Apr 25, 2011 at 7:39 PM

Alright I dug around some more in the source and have come up with this with the following piece of code.  I am attempting to create a contentitem via code and navigate to it via the brower.

      _services = services;
      _routableService = routableService;
     
      //var myPart = _services.ContentManager.New<CoursePart>("ReCPro");
      
      CoursePart myPart = new CoursePart();
      myPart.Record = new CoursePartRecord();
      myPart.ActivityID = 15;
      myPart.Number = "MyNumber";
      myPart.Season = "MySeason";
      myPart.Year = "2011";
      myPart.Title = "MyTitle";
      
      //_routableService.ProcessSlug(myPart.As<IRoutableAspect>());

      var myContentTypeBuilder = new ContentTypeDefinitionBuilder().Named("helloWorld5").DisplayedAs("helloWorld5").Build();
      var hello = new ContentItemBuilder(myContentTypeBuilder)
      .Weld<CommonPart>()
      .Weld<RoutePart>()
        //.Weld<BodyPart>()
      .Weld(myPart)
      .Build();

      

      hello.As<CommonPart>().Record = new CommonPartRecord();
      hello.As<RoutePart>().Record = new RoutePartRecord();
      //hello.As<BodyPart>().Record = new BodyPartRecord();

      hello.As<CommonPart>().PublishedUtc = DateTime.UtcNow;// clock.UtcNow;
      hello.As<RoutePart>().Title = "alpha3";
      hello.As<RoutePart>().Slug = "beta3";
      hello.As<RoutePart>().Path = hello.As<RoutePart>().GetPathWithSlug(hello.As<RoutePart>().Slug);

      
      contentDefintionManager.StoreTypeDefinition(myContentTypeBuilder);

      _services.ContentManager.Create(hello, VersionOptions.Published);

everything seems to be created correct in the database, but the routing is not working...  

In Orchard.Web\Core\Routable\Controlelrs\ItemController.cs\Display(string path) this piece of code

            var hits = _contentManager
                .Query<RoutePart, RoutePartRecord>(VersionOptions.Published)
                .Where(r => r.Path == matchedPath)
                .Slice(0, 2);
            if (hits.Count() == 0) {
                throw new ApplicationException(T("404 - should not have passed path constraint").Text);
            }
hits.Count() is 0.

Apr 26, 2011 at 2:51 PM
Edited Apr 26, 2011 at 2:52 PM

Anyone? Anything? Am I far off base? Close?

Apr 26, 2011 at 3:10 PM

I think Weld is just for attaching a part at runtime; it won't store that part in the database. It gets used normally when items are loaded from the database.

You have to use the ContentTypeDefinitionBuilder to define what database parts will exist for that item.

At least, I think that's the case, although that part of the system is all a bit abstract and complex. But you should look at the ContentTypes module and see how the UI-built types are created.

Apr 26, 2011 at 3:31 PM

That code actually adds all of the parts associated with the helloWorld type to the database, the course part, common part and route part are all represented in the database.  Its just when I try navigate to the slug, I get an error.  

 

But taking a look at the ContentTypes module, that looks promising I'll start looking through that.  

Thanks for the direction.

Coordinator
Apr 26, 2011 at 3:56 PM

They are in the database, at the content item level, not at the metadata level, thus the system doesn't know it contains them. You should really use randompete's suggestion here, in addition to what you are currently doing.

Apr 26, 2011 at 8:55 PM

Finally got it to work...  I was almost there just missed one thing on my ContentTypeDefinitionBuilder.  I didn't have the with part's.  Added those everything worked

      var myContentTypeBuilder = new ContentTypeDefinitionBuilder().Named("helloWorld48").DisplayedAs("helloWorld48")
                                                                   .WithPart("CommonPart")
                                                                   .WithPart("RoutePart")
                                                                   .WithPart("CoursePart")
                                                                   .Build();
Thanks for the suggestions.