Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Complicated Module Based Create new Record in DB with ASP.NET MVC 2

I have a very tough problem for me to solve, and I thought and searched alot and came down t one conclusion which I will mention down. the problem is I have a client that wants to create a websites based on a Common functionality, so let us call it Modules, so what I thought is to use MVC Contrib Portable Areas, which are great ideas to plug Modules, but I have a big problem, let us say I created a Blog module which will be implemented in a new site he want, now some users have unique requirements like one of them needs to add Gallery of pictures to each article, or List of references in each article. this would be easy in normal situation where you have one site to work on, so all what you have to do is

  • add a new gallery table with Foreign key to the Blog table.
  • regenerate Linq2SQl code and update the Model.
  • add new form elements to the Create, Edit, Delete Views .
  • add the logic in the controller.

but in my situation it is complicated and time cumbersome because of 2 reasons

  • if the new functionality is cool and client decide to implement it in all sites, then I have to repeat the work for each site.
  • if the functionality is unique it will create inconsistency for me in future

that is why as first step to solve the problem I used Portable Areas to create Addons for each Module, now this will definitely ease my work by dragging 1 DLL for each new Module or Addon, but I have a little problem here, which

  • because the new Module or Addin is a Dll, how can I create such a functionality in My Admin panel to install the new Addon or find any new added Module/Addon dragged new DLLS to the Main Application
  • What is best practice to create an installation procedure inside the Portable Area, like Update the DB, New Routes, etc..

Now to the biggest Problem which is specific to Module Addon :) let us take back the Article Gallery Addon, if I follow the logic I have mentioned above by creating it as a Portable area, it would be easier to create a functionality in the Module Code to loop through all Installed Addons and list them in the CRUD Views, but because I isolated the Addon and don't want to manually update the Main Module Code for the Reasons Above there will be no way for doing CRUD operations for the new Addons in Sync with the main module because there is no Foreign Key Relation, again because as I said above it may be Optional, so I thought of the following solution which I hope there would be a better one

First in Installation Process I will create a Table for the Gallery Addon, but instead of creating a foreign Key relation I will create a manual Foreign Key which will get populated by Generating a Unique ID in the Main Module Controller when I create record by using the following code then store it in ViewData and just pass it to the Addon Controller when I create the new Record,

private  string GenerateId()
 {
  long i = 1;
  foreach (byte b in Guid.NewGuid().ToByteArray())
  {
   i *= ((int)b + 1);
  }
  return string.Format("{0:x}", i - DateTime.Now.Ticks);
 }
ViewData["FK"] = GenerateId();

but here are my Concerns

  • Is this way feasible or just plain Stupid.
  • is this technique will generate a truly unique key.

I am extremely sorry if my question is lame, but this is the best place to ask and I think many people would want to have such a functionality and hope someone will answer me

like image 414
DevMania Avatar asked Nov 05 '22 11:11

DevMania


1 Answers

I think it's a great question. awhile ago I started working on a CMS project using MVC1, where I wanted to support plugins. I had it working so that the admin could drop a new plugin assembly into the bin folder, and next app start, it would scan all assemblies for IPlugin (or whatever) and load them. I embedded the partial views into the plugin assembly so it was all self contained. each plugin was given a unique identifier when it was placed on a page, and the plugin's controller knew how to use that ID to query it's own table (repository) for it's data. the main application didn't know anything about the plugin's schema.

the only difference here is that it sounds like you would have multiple websites running on the same database, and you need to differentiate which instances of the plugin you need for each website. I assume somewhere you've got a key that indicates which website it is, that could be used via foreign key to select only the plugins for that website for the page the user is on.

I'm not sure if this is an answer, I'm sort of just thinking out loud. hopefully it'll help the discussion a little.

EDIT: To automatically load plugins, I used NInject's ability to scan assemblies for IModules. My IPlugin inherits from Ninject.Modules.INinjectModule, and all plugins implement the IPlugin interface. Then on app startup, I have the following line:

kernel.Load( "*.Plugin.dll" );

where kernel is a Ninject.IKernel and that line will scan any assembly matching that file pattern, so I could drop in an assembly like Weather.Plugin.dll.

like image 82
Dave Thieben Avatar answered Nov 13 '22 08:11

Dave Thieben