Posted
over 11 years
ago
I have been asked a few times on how to create your own table
and add it into MVCForum. I have already created a blog about adding your own custom
table and this is a follow up to that post.
In the previous post we created a table called
... [More]
BannedWord and created a domain class of the same
name and mapped it to the database. You can now query that table
from within an existing repository that has a context. But its not
an ideal situation, as we have tried to create a very DDD pattern and allow you to be able to swap
out services and repos with ease just by changing a couple of lines
in the IOC container.
In the current application we have a
BannedWordService and a
BannedWordRepository and in the post below I'll
explain how I added them and use them, so you can do the same for
you own custom table/Domain model and keep the same structure as
you customise your own forum.
Before you delve in, I must say. When I first started developing
this way, I thought it was so long winded. But now after using it
for a while I can see how beneficial it is and its pretty quick to
setup after you have done it a few times.
Interfaces
First thing we need to do is create a couple of interfaces
within the MVCForum.Domain > Interfaces section. One for the
Service and one for the Repository (Repo). Then within these
interfaces we will add in the method signatures that we think we'll
need to use.
Don't worry you can always add more later down the line (In fact
I pretty much always end up adding another one or two). The methods
you add are usually just CRUD methods.
MVCForum.Domain > Interfaces > Repositories
This is where we create the Repo interface and you prefix all
interfaces with IYourDomainName. Here is the
IBannedWordRepository.
using System;
using System.Collections.Generic;
using MVCForum.Domain.DomainModel;
namespace MVCForum.Domain.Interfaces.Repositories
{
public interface IBannedWordRepository
{
BannedWord Add(BannedWord bannedWord);
void Delete(BannedWord bannedWord);
IList<BannedWord> GetAll();
BannedWord Get(Guid id);
PagedList<BannedWord> GetAllPaged(int pageIndex, int pageSize);
PagedList<BannedWord> GetAllPaged(string search, int pageIndex, int pageSize);
}
}
MVCForum.Domain > Interfaces > Services
And here is the IBannedWordService I have added. You'll see the
methods are pretty much the same as the Repo. Around 95% of the
time it will be the same as the repo, but I'll go into more detail
further down about the difference between the two.
using System;
using System.Collections.Generic;
using MVCForum.Domain.DomainModel;
namespace MVCForum.Domain.Interfaces.Services
{
public interface IBannedWordService
{
BannedWord Add(BannedWord bannedWord);
void Delete(BannedWord bannedWord);
IList<BannedWord> GetAll();
BannedWord Get(Guid id);
PagedList<BannedWord> GetAllPaged(int pageIndex, int pageSize);
PagedList<BannedWord> GetAllPaged(string search, int pageIndex, int pageSize);
string SanitiseBannedWords(string content);
string SanitiseBannedWords(string content, IList<string> words);
}
}
Implementing The Interfaces (Creating the Service &
Repo)
Now we have created both the above interfaces, we can implement
them in the appropriate places. If you don't know about interfaces
and how to implement them, then I really suggest you have a read up
online.
However in short, its very simple and just a matter of creating
a class i.e. BannedWordRepository and then at the top of the class
next to the class name. You just add a colon : and
then interface name (i.e. public class BannedWordRepository
: IBannedWordRepository) then visual studio will pick up
on this and hopefully prompt you and create the method stubs for
you.
MVCForum.Data > Repositories
We'll create the repo first. BUT one thing you will notice. In
pretty much every repo, we add a Constructor and within that add
the context (The context is how we query the DBsets/Domain models
via
Entity Framework). This is resolved by IOC (See below) so you
can get access to the database. Don't forget to add/update this or
you won't be able to query the data as no context will exist.
using System;
using System.Collections.Generic;
using System.Linq;
using MVCForum.Data.Context;
using MVCForum.Domain.DomainModel;
using MVCForum.Domain.Interfaces;
using MVCForum.Domain.Interfaces.Repositories;
namespace MVCForum.Data.Repositories
{
public class BannedWordRepository : IBannedWordRepository
{
private readonly MVCForumContext _context;
public BannedWordRepository(IMVCForumContext context)
{
_context = context as MVCForumContext;
}
public BannedWord Add(BannedWord bannedWord)
{
return _context.BannedWord.Add(bannedWord);
}
public void Delete(BannedWord bannedWord)
{
_context.BannedWord.Remove(bannedWord);
}
public IList<BannedWord> GetAll()
{
return _context.BannedWord.OrderByDescending(x => x.DateAdded).ToList();
}
public BannedWord Get(Guid id)
{
return _context.BannedWord.FirstOrDefault(x => x.Id == id);
}
public PagedList<BannedWord> GetAllPaged(int pageIndex, int pageSize)
{
var total = _context.BannedWord.Count();
var results = _context.BannedWord
.OrderBy(x => x.Word)
.Skip((pageIndex - 1) * pageSize)
.Take(pageSize)
.ToList();
return new PagedList<BannedWord>(results, pageIndex, pageSize, total);
}
public PagedList<BannedWord> GetAllPaged(string search, int pageIndex, int pageSize)
{
var total = _context.BannedWord.Count(x => x.Word.ToLower().Contains(search.ToLower()));
var results = _context.BannedWord
.Where(x => x.Word.ToLower().Contains(search.ToLower()))
.OrderBy(x => x.Word)
.Skip((pageIndex - 1) * pageSize)
.Take(pageSize)
.ToList();
return new PagedList<BannedWord>(results, pageIndex, pageSize, total);
}
}
}
MVCForum.Data > MVCForum.Services
Now we add the service. And again as with the context in the
constructor of the Repo. This time, in the constructor of the class
we pull in the Repo we just created so we can get access to the
data.
The difference between the two classes is like this. The Repo
should be purely for getting data and returning it. The service is
for getting the data and then doing any complicated logic before it
passes it on (i.e. Remapping, filtering, sanitising content etc…).
So here is our Service.
using System;
using System.Linq;
using System.Collections.Generic;
using MVCForum.Domain.DomainModel;
using MVCForum.Domain.Interfaces.Repositories;
using MVCForum.Domain.Interfaces.Services;
using MVCForum.Utilities;
namespace MVCForum.Services
{
public class BannedWordService : IBannedWordService
{
private readonly IBannedWordRepository _bannedWordRepository;
public BannedWordService(IBannedWordRepository bannedWordRepository)
{
_bannedWordRepository = bannedWordRepository;
}
public BannedWord Add(BannedWord bannedWord)
{
return _bannedWordRepository.Add(bannedWord);
}
public void Delete(BannedWord bannedWord)
{
_bannedWordRepository.Delete(bannedWord);
}
public IList<BannedWord> GetAll()
{
return _bannedWordRepository.GetAll();
}
public BannedWord Get(Guid id)
{
return _bannedWordRepository.Get(id);
}
public PagedList<BannedWord> GetAllPaged(int pageIndex, int pageSize)
{
return _bannedWordRepository.GetAllPaged(pageIndex, pageSize);
}
public PagedList<BannedWord> GetAllPaged(string search, int pageIndex, int pageSize)
{
return _bannedWordRepository.GetAllPaged(search, pageIndex, pageSize);
}
public string SanitiseBannedWords(string content)
{
var bannedWords = GetAll();
if (bannedWords.Any())
{
return SanitiseBannedWords(content, bannedWords.Select(x => x.Word).ToList());
}
return content;
}
public string SanitiseBannedWords(string content, IList<string> words)
{
if (words != null && words.Any())
{
var censor = new CensorUtils(words);
return censor.CensorText(content);
}
return content;
}
}
}
You'll notice at the bottom there is a CensorUtils class. This
is something that is added in v1.3 to the forum. If you are
following this word for word, then just remove both
SanitiseBannedWords methods from the interface and implementation
as you won't need them for this tutorial.
Registering With The IOC Container
Once you have created both your Service and Repository you need
to register them in with the IOC container (We currently use
Unity for our IoC), or the repo in the service constructor
above won't work and you won't be able to use your service in the
controllers.
MVCForum.IOC > UnityMVC3.cs
This is a really simple couple of lines to add. Just open the
above file and add in the following for the service and repo.
container.BindInRequestScope<IBannedWordService, BannedWordService>();
container.BindInRequestScope<IBannedWordRepository, BannedWordRepository>();
It should be pretty self explanatory where to add these, the
services are all grouped together and so are the repos. All this
file does it point the interface to which implementation of the
interface to use. So you can swap out implementations top custom
ones if you want to.
Using The Service In A Controller
As you will see throughout and I mentioned above. The repo is
never used apart from by the services. They simply just
transfer/update/delete data from the database. But the services are
what you use and call from within the application.
So to get the data back and use what we have just created, we
need to call the service from your controller. This is very simple
and the same as how we called the Repo from within our service. We
just setup a constructor and initialise the service interface we
want to use and the IOC container will take care of the rest and
get the correct implementation.
For example. If I wanted to create a
BannedWordController then I would set it up like
this with the service in the constructor
using System.Web.Mvc;
using MVCForum.Domain.Interfaces.Services;
namespace MVCForum.Website.Controllers
{
public class BannedWordController : Controller
{
private readonly IBannedWordService _bannedWordService;
public BannedWordController(IBannedWordService bannedWordService)
{
_bannedWordService = bannedWordService;
}
public ActionResult Index()
{ // I can now use the service here by called
var getAllBannedWords = _bannedWordService.GetAll(); return View();
}
}
}
And that's it. We can call the service from any controller we
want as long as we set it up in the constructor like the above
example. [Less]
|
Posted
over 11 years
ago
If you want to add a new table and start using it within your
forum, its pretty straight forward. I'm in the middle of developing
v1.3, and I'm just about to add a BannedWord table for storing
banned words in so I'll walk you through how I add it.
... [More]
Because of the way the caching is implemented, you will get
caching out the box for your new table.
1) Add your table
Create your table, making sure you add Id as your primary key
and set it to 'uniqueidentifier' as below we set the Id to our
CombGuid generator.
2) Add your Domain Model
MVCForum.Domain > DomainModel
Your domain model is what you code against/with through out your
application. To keep things simple just create a class with the
same name as your table and then add in properties to match your
fields from the database.
Add a Constuctor and assign Id to GuidComb.GenerateComb() as
this gives us sequential Guids and helps with SQL performance. Here
is my domain class for the BannedWord table.
using System;
using MVCForum.Utilities;
namespace MVCForum.Domain.DomainModel
{
public class BannedWord
{
public BannedWord()
{
Id = GuidComb.GenerateComb();
}
public Guid Id { get; set; }
public string Word { get; set; }
public DateTime DateAdded { get; set; }
}
}
3) Map Model to the database
MVCForum.Data > Mapping
Firstly we need to create a Mapping class for this domain model
you just created. This one will be pretty simple as we are not
doing any joins with other tables. If you want to see how joins are
mapped, then have a look in the TopicMapping.cs file.
using System.Data.Entity.ModelConfiguration;
using MVCForum.Domain.DomainModel;
namespace MVCForum.Data.Mapping
{
public class BannedWordMapping : EntityTypeConfiguration<BannedWord>
{
public BannedWordMapping()
{
HasKey(x => x.Id);
}
}
}
Once this is done we need to hook up the table with the Entity
Framework context. This is very simple and just a couple of
lines.
MVCForum.Data > Context >
MVCForumContext.cs
Add this line where the other DbSet's for the existing tables
are
public DbSet<BannedWord> BannedWord { get; set; }
Then at the bottom of this class within the
OnModelCreating(DbModelBuilder modelBuilder) method, add this
line.
modelBuilder.Configurations.Add(new BannedWordMapping());
That's it
That is everything you need to do, to start querying against the
database from one of the Repositories. For example I could use the
MVCforumcontext and now get back all BannedWord's ordered by
date added like so.
_context.BannedWord.OrderBy(x => x.DateAdded).ToList()
Structure
If you do this. Then it would be highly recommended that you
keep the interfaced DDD pattern that we currently have. And create
a BannedWordService & BannedWordRepository. I'll go into
the structure in another blog post. [Less]
|
Posted
over 11 years
ago
If you want to add a new table and start using it within your
forum, its pretty straight forward. I'm in the middle of developing
v1.3, and I'm just about to add a BannedWord table for storing
banned words in so I'll walk you through how I add it.
... [More]
Because of the way the caching is implemented, you will get
caching out the box for your new table.
1) Add your table
Create your table, making sure you add Id as your primary key
and set it to 'uniqueidentifier' as below we set the Id to our
CombGuid generator.
2) Add your Domain Model
MVCForum.Domain > DomainModel
Your domain model is what you code against/with through out your
application. To keep things simple just create a class with the
same name as your table and then add in properties to match your
fields from the database.
Add a Constuctor and assign Id to GuidComb.GenerateComb() as
this gives us sequential Guids and helps with SQL performance. Here
is my domain class for the BannedWord table.
using System;
using MVCForum.Utilities;
namespace MVCForum.Domain.DomainModel
{
public class BannedWord
{
public BannedWord()
{
Id = GuidComb.GenerateComb();
}
public Guid Id { get; set; }
public string Word { get; set; }
public DateTime DateAdded { get; set; }
}
}
3) Map Model to the database
MVCForum.Data > Mapping
Firstly we need to create a Mapping class for this domain model
you just created. This one will be pretty simple as we are not
doing any joins with other tables. If you want to see how joins are
mapped, then have a look in the TopicMapping.cs file.
using System.Data.Entity.ModelConfiguration;
using MVCForum.Domain.DomainModel;
namespace MVCForum.Data.Mapping
{
public class BannedWordMapping : EntityTypeConfiguration<BannedWord>
{
public BannedWordMapping()
{
HasKey(x => x.Id);
}
}
}
Once this is done we need to hook up the table with the Entity
Framework context. This is very simple and just a couple of
lines.
MVCForum.Data > Context >
MVCForumContext.cs
Add this line where the other DbSet's for the existing tables
are
public DbSet<BannedWord> BannedWord { get; set; }
Then at the bottom of this class within the
OnModelCreating(DbModelBuilder modelBuilder) method, add this
line.
modelBuilder.Configurations.Add(new BannedWordMapping());
That's it
That is everything you need to do, to start querying against the
database from one of the Repositories. For example I could use the
MVCforumcontext and now get back all BannedWord's ordered by
date added like so.
_context.BannedWord.OrderBy(x => x.DateAdded).ToList()
Structure
If you do this. Then it would be highly recommended that you
keep the interfaced DDD pattern that we currently have. And create
a BannedWordService & BannedWordRepository. I'll go into
the structure in another blog post.
[Less]
|
Posted
over 11 years
ago
If you want to add a new table and start using it within your
forum, its pretty straight forward. I'm in the middle of developing
v1.3, and I'm just about to add a BannedWord table for storing
banned words in so I'll walk you through how I add it.
... [More]
Because of the way the caching is implemented, you will get
caching out the box for your new table.
1) Add your table
Create your table, making sure you add Id as your primary key
and set it to 'uniqueidentifier' as below we set the Id to our
CombGuid generator.
2) Add your Domain Model
MVCForum.Domain > DomainModel
Your domain model is what you code against/with through out your
application. To keep things simple just create a class with the
same name as your table and then add in properties to match your
fields from the database.
Add a Constuctor and assign Id to GuidComb.GenerateComb() as
this gives us sequential Guids and helps with SQL performance. Here
is my domain class for the BannedWord table.
using System;
using MVCForum.Utilities;
namespace MVCForum.Domain.DomainModel
{
public class BannedWord
{
public BannedWord()
{
Id = GuidComb.GenerateComb();
}
public Guid Id { get; set; }
public string Word { get; set; }
public DateTime DateAdded { get; set; }
}
}
3) Map Model to the database
MVCForum.Data > Mapping
Firstly we need to create a Mapping class for this domain model
you just created. This one will be pretty simple as we are not
doing any joins with other tables. If you want to see how joins are
mapped, then have a look in the TopicMapping.cs file.
using System.Data.Entity.ModelConfiguration;
using MVCForum.Domain.DomainModel;
namespace MVCForum.Data.Mapping
{
public class BannedWordMapping : EntityTypeConfiguration<BannedWord>
{
public BannedWordMapping()
{
HasKey(x => x.Id);
}
}
}
Once this is done we need to hook up the table with the Entity
Framework context. This is very simple and just a couple of
lines.
MVCForum.Data > Context >
MVCForumContext.cs
Add this line where the other DbSet's for the existing tables
are
public DbSet<BannedWord> BannedWord { get; set; }
Then at the bottom of this class within the
OnModelCreating(DbModelBuilder modelBuilder) method, add this
line.
modelBuilder.Configurations.Add(new BannedWordMapping());
That's it
That is everything you need to do, to start querying against the
database from one of the Repositories. For example I could use the
MVCforumcontext and now get back all BannedWord's ordered by
date added like so.
_context.BannedWord.OrderBy(x => x.DateAdded).ToList()
Structure
If you do this. Then it would be highly recommended that you
keep the interfaced DDD pattern that we currently have. And create
a BannedWordService & BannedWordRepository. I'll go into
the structure in another blog post. [Less]
|
Posted
almost 12 years
ago
We have done this on a few child actions by default, but if you
are customising the forum and adding your own widgets then consider
adding it.
Adding Output Cache To Controller Actions
You can decorate Actions with the output cache like so
... [More]
[OutputCache(Duration = AppConstants.DefaultCacheLengthInSeconds)]
Where duration is the time you want to cache it in seconds
(We have a constant set as you can see). We use this
for the RSS feeds already and other child actions, but if you have
any data that doesn't need to be instantly updated the moment a
user makes a change then you should consider adding this.
There are a few overloads and other settings you can add, so to
read more about Output cache and other things you can do with it then go here
Speed Tip! We Recommend Adding…
On the side of the default install of MVC Forum you have a few
side menus which are partial views/child actions. We have added
Output Cache to most of them except the below.
[ChildActionOnly]
public PartialViewResult ListCategorySideMenu()
We recommend you add it to this child action, so it becomes:
[ChildActionOnly]
[OutputCache(Duration = AppConstants.DefaultCacheLengthInSeconds)]
public PartialViewResult ListCategorySideMenu()
Reason we didn't add it by default is because people were
changing the categories, and then complaining the site wasn't
updating as they didn't realise it had the output cache added.
So we removed it to stop the posts/emails, and instead will just
recommend you add it yourself just before you put your forum
live. [Less]
|
Posted
almost 12 years
ago
We have done this on a few child actions by default, but if you
are customising the forum and adding your own widgets then consider
adding it.
Adding Output Cache To Controller Actions
You can decorate Actions with the output cache like so
... [More]
[OutputCache(Duration = AppConstants.DefaultCacheLengthInSeconds)]
Where duration is the time you want to cache it in seconds
(We have a constant set as you can see). We use this
for the RSS feeds already and other child actions, but if you have
any data that doesn't need to be instantly updated the moment a
user makes a change then you should consider adding this.
There are a few overloads and other settings you can add, so to
read more about Output cache and other things you can do with it then go here
Speed Tip! We Recommend Adding…
On the side of the default install of MVC Forum you have a few
side menus which are partial views/child actions. We have added
Output Cache to most of them except the below.
[ChildActionOnly]
public PartialViewResult ListCategorySideMenu()
We recommend you add it to this child action, so it becomes:
[ChildActionOnly]
[OutputCache(Duration = AppConstants.DefaultCacheLengthInSeconds)]
public PartialViewResult ListCategorySideMenu()
Reason we didn't add it by default is because people were
changing the categories, and then complaining the site wasn't
updating as they didn't realise it had the output cache added.
So we removed it to stop the posts/emails, and instead will just
recommend you add it yourself just before you put your forum
live. [Less]
|
Posted
almost 12 years
ago
We have done this on a few child actions by default, but if you
are customising the forum and adding your own widgets then consider
adding it.
Adding Output Cache To Controller Actions
You can decorate Actions with the output cache like so
... [More]
[OutputCache(Duration = AppConstants.DefaultCacheLengthInSeconds)]
Where duration is the time you want to cache it in seconds
(We have a constant set as you can see). We use this
for the RSS feeds already and other child actions, but if you have
any data that doesn't need to be instantly updated the moment a
user makes a change then you should consider adding this.
There are a few overloads and other settings you can add, so to
read more about Output cache and other things you can do with it then go here
Speed Tip! We Recommend Adding…
On the side of the default install of MVC Forum you have a few
side menus which are partial views/child actions. We have added
Output Cache to most of them except the below.
[ChildActionOnly]
public PartialViewResult ListCategorySideMenu()
We recommend you add it to this child action, so it becomes:
[ChildActionOnly]
[OutputCache(Duration = AppConstants.DefaultCacheLengthInSeconds)]
public PartialViewResult ListCategorySideMenu()
Reason we didn't add it by default is because people were
changing the categories, and then complaining the site wasn't
updating as they didn't realise it had the output cache added.
So we removed it to stop the posts/emails, and instead will just
recommend you add it yourself just before you put your forum
live.
[Less]
|
Posted
almost 12 years
ago
We have released v1.2 this morning. There are no major
functionality/feature changes, just a lot of bug fixes and changes
to the input sanitizing which was over the top and causing issues
for some forums in languages other than English. Grab it from
... [More]
codeplex via the link below:
http://themvcforum.codeplex.com/
We'll be updating the WebPI version today/tomorrow.
Codeplex
We caused a lot of our own problems by not creating branches on
codeplex for different versions, which annoyed a lot of people as
you were downloading the latest code on codeplex but it wouldn't
build or was not compatible with your version.
We're are now changing this, and we'll try to work in a more
stuctured way on codeplex. We are still learning the whole
branching and open source thing so bear with us.
Bugs
As always if you find any bugs or something is not working as
you expect it to. Then please can you report them on the forum or
on codeplex
http://themvcforum.codeplex.com/workitem/list/basic
[Less]
|
Posted
almost 12 years
ago
We have released v1.2 this morning. There are no major
functionality/feature changes, just a lot of bug fixes and changes
to the input sanitizing which was over the top and causing issues
for some forums in languages other than English. Grab it
... [More]
from
codeplex via the link below:
http://themvcforum.codeplex.com/
We'll be updating the WebPI version today/tomorrow.
Codeplex
We caused a lot of our own problems by not creating branches on
codeplex for different versions, which annoyed a lot of people as
you were downloading the latest code on codeplex but it wouldn't
build or was not compatible with your version.
We're are now changing this, and we'll try to work in a more
stuctured way on codeplex. We are still learning the whole
branching and open source thing so bear with us.
Bugs
As always if you find any bugs or something is not working as
you expect it to. Then please can you report them on the forum or
on codeplex
http://themvcforum.codeplex.com/workitem/list/basic [Less]
|
Posted
about 12 years
ago
We had to make a difficult decision this week. And that was
whether we continued trying to develop the installer to upgrade
users on v1.0 to v1.1.
Our intention was always to have the installer work as an
upgrader for all versions, and this is
... [More]
still our intention.
However, the amount of changes and updates from v1.0 to v1.1 is
making that difficult and hindering us to get v1.1 released (We got
a little carried away adding features and changes).
Moving forward from v1.1, we'll definitely be developing the
installer as an upgrader too. So any future versions will be fine.
So if you do want to upgrade from v1.0 to v1.1 then please follow
the instructions below.
1.) Install a blank v1.1
This is because you can use it as a reference and copy across
files to you v1.0 version and compare the databases if things don't
work as they should.
1.1) Add New Data To Current v1.0 Db
In your existing v1.0 forum, open up the admin section and add
the following
1.1.1) Go to the Permissions section and add the
following new Permission Type (Exactly as below)
Vote In Polls
1.1.2) In the Language section and add the following
Language keys and then the values
Topic.Label.TopicTitle = Title
Poll.Button.Create = Add A Poll To This Topic
Poll.Button.Remove = Remove Poll From Topic
Poll.Placeholder.TypeAnswerHere = Type A Poll Answer Here
Topic.OptionsHeading = Topic Options
Poll.Button.Vote = Submit Vote
Error.WrongAnswerRegistration = There was an error with your
answer, please try again
Members.LoginOrText = Or
Facebook.Error.EnabledButNotAddedKeys = You have enabled Facebook
login but not added your AppId or Secret key to the
web.config
Members.Profile.IsSocialAccount = Social Account
2.) Update your web.config
In the appsettings section add the following
<add key="FacebookAppId" value="" />
<add key="FacebookAppSecret" value="" />
In the system.web section add the following
<httpRuntime requestValidationMode="2.0"
requestPathInvalidCharacters="*,:,&,\"
relaxedUrlToFileSystemMapping="true" maxQueryStringLength="2048" />
<globalization fileEncoding="utf-8" requestEncoding="utf-8" responseEncoding="utf-8" />
In the system.webServer section add the following
<security>
<requestFiltering allowDoubleEscaping="true"/>
security>
Update the version to 1.1 in the app settings to the
following
<add key="MVCForumVersion" value="1.1" />
3.) Update the database
This part is the trickiest part, and why I said to install a
blank v1.1 in the first step. Follow the instructions below, and
once done then double check them against the blank v1.1 database to
be sure. Also be sure to check the VersionDbChanges.txt in the
source which has all changes per version.
Also if you are handy with SQL, the full v1.1 database creation
script is in the 'Database' solution folder called
mvcforum-v1.1.sql so you might be able to adapt
that to make this process easier.
3.1) Add primary key to Activity Table 'Id'
field
3.2) Add primary key to BadgeTypeTimeLastChecked Table
'Id' field
3.3) 'Topic' table
- Add Poll_Id (Guid) allow nulls
- Update name to nvarchar(450)
- Update slug to nvarchar(450)
3.4) 'Category' Table
- Update name to nvarchar(450)
- Update slug to nvarchar(450)
3.5) 'TopicTag' Table
- Update name to nvarchar(100)
3.4) Add new Table 'Poll' and foreign keys, use the SQL
below
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[Poll](
[Id] [uniqueidentifier] NOT NULL,
[IsClosed] [bit] NOT NULL,
[MembershipUser_Id] [uniqueidentifier] NOT NULL,
[DateCreated] [datetime] NOT NULL,
CONSTRAINT [PK_Poll] PRIMARY KEY CLUSTERED
(
[Id] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
GO
ALTER TABLE [dbo].[Poll] WITH CHECK ADD CONSTRAINT [FK_Poll_MembershipUser] FOREIGN KEY([MembershipUser_Id])
REFERENCES [dbo].[MembershipUser] ([Id])
GO
ALTER TABLE [dbo].[Poll] CHECK CONSTRAINT [FK_Poll_MembershipUser]
GO
ALTER TABLE [dbo].[Poll] ADD CONSTRAINT [DF_Poll_IsClosed] DEFAULT ((0)) FOR [IsClosed]
GO
3.5) Add new Table 'PollAnswer' and foreign keys, use
the SQL below
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[PollAnswer](
[Id] [uniqueidentifier] NOT NULL,
[Answer] [nvarchar](600) NOT NULL,
[Poll_Id] [uniqueidentifier] NOT NULL,
CONSTRAINT [PK_PollAnswer] PRIMARY KEY CLUSTERED
(
[Id] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
GO
ALTER TABLE [dbo].[PollAnswer] WITH CHECK ADD CONSTRAINT [FK_PollAnswer_Poll] FOREIGN KEY([Poll_Id])
REFERENCES [dbo].[Poll] ([Id])
GO
ALTER TABLE [dbo].[PollAnswer] CHECK CONSTRAINT [FK_PollAnswer_Poll]
GO
3.6) Add new Table 'PollVote' and foreign keys, use the
SQL below
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[PollVote](
[Id] [uniqueidentifier] NOT NULL,
[MembershipUser_Id] [uniqueidentifier] NOT NULL,
[PollAnswer_Id] [uniqueidentifier] NOT NULL,
CONSTRAINT [PK_PollVote] PRIMARY KEY CLUSTERED
(
[Id] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
GO
ALTER TABLE [dbo].[PollVote] WITH CHECK ADD CONSTRAINT [FK_PollVote_MembershipUser] FOREIGN KEY([MembershipUser_Id])
REFERENCES [dbo].[MembershipUser] ([Id])
GO
ALTER TABLE [dbo].[PollVote] CHECK CONSTRAINT [FK_PollVote_MembershipUser]
GO
ALTER TABLE [dbo].[PollVote] WITH CHECK ADD CONSTRAINT [FK_PollVote_PollAnswer] FOREIGN KEY([PollAnswer_Id])
REFERENCES [dbo].[PollAnswer] ([Id])
GO
ALTER TABLE [dbo].[PollVote] CHECK CONSTRAINT [FK_PollVote_PollAnswer]
GO
3.7) Update the 'Settings' table with the following new
fields
EnableAkisment (bit) allow nulls
AkismentKey (nvarchar(100)) allow nulls
CurrentDatabaseVersion (nvarchar(10)) allow nulls
SMTPPort (nvarchar(10)) allow nulls
SpamQuestion (nvarchar(500)) allow nulls
SpamAnswer (nvarchar(500)) allow nulls
SMTPEnableSSL (bit) allow nulls
EnableSocialLogins (bit) allow nulls
EnablePolls (bit) allow nulls
3.8) Update the 'Post' table with the following new
field
FlaggedAsSpam (bit) allow nulls
3.9) Update the 'MembershipUser' table with the
following new fields
Avatar (nvarchar(250)) allow nulls
FacebookAccessToken (nvarchar(150)) allow nulls
FacebookId (bigint) allow nulls
TwitterAccessToken (nvarchar(150)) allow nulls
TwitterId (nvarchar(150)) allow nulls
GoogleAccessToken (nvarchar(150)) allow nulls
GoogleId (nvarchar(150)) allow nulls
MiscAccessToken (nvarchar(150)) allow nulls
IsExternalAccount (bit) allow nulls
TwitterShowFeed (bit) allow nulls
LoginIdExpires (datetime) allow nulls
Latitude (nvarchar(40)) allow nulls
Longitude (nvarchar(40)) allow nulls
And the update the following existing fields
Update UserName to nvarchar(150)
Update slug to nvarchar(150)
4.) Copy Across The Files
Now just copy across the files apart from the web.config from
the blank install of v1.1 you made and over write the files in your
v1.0 forum.
And that 'should' be it, and you're good to go. [Less]
|