1

I have the model (code first) & database (SQL Server) setup with many to many relationship & seeding fine:

A Place can have many tags (eg Restaurant, bar, cafe) - and tags can belong to many places.

Place
[ScaffoldColumn(false)]
public virtual int PlaceID { get; set; }

[Required(ErrorMessage = "Place Name is required")]
[StringLength(100)]
public virtual string Name { get; set; }

[Required]
public virtual string Address {get;set;}

public virtual string ImageLogo {get;set;}
public virtual string ImageBackground {get;set;}


Tag
public virtual int TagID { get; set; }

[Required]
public virtual string Name { get; set; }

[Required]
public virtual string NamePlural { get; set; }

public virtual ICollection<Place> Places { get; set; }

EF Migrations has generated a junction table with TagID & PlaceID and I can add Places with multiple tags fine in my Seed method. There are about 50 tags - all seeded.

What I would like to do is have a Create view form - that allows users to select from all the tags - maybe with check boxes (open to alternatives), some async textbox etc? Which are then saved with the model.

This data will be entered by an administrator - speed of entry is most important (doesn't have to be 100% idiot proof).

I also need to be able to edit the place - and have those tags show up appropriately to be removed or others added.

Also the best way to handle deletion of places - delete records in junction table first?

What is best practice in all of the above?

Thanks.

1 Answer 1

1

I think the best and simplest way for you is that you have a view for creating Place and at the bottom of it put a fieldset to assign tags to it.

For the fieldset, you should mave two partial views: One for create and another for edit. The partial view for creating should be somthing like this:

@model myPrj.Models.PlaceTagInfo

@{ 
    var index = Guid.NewGuid().ToString(); 
    string ln = (string)ViewBag.ListName;
    string hn = ln + ".Index";
}

<tr>
    <td>        
        <input type="hidden" name="@hn" value="@index" />
        @Html.LabelFor(model => model.TagID)
    </td>
    <td>
        @Html.DropDownList(ln + "[" + index + "].TagID", 
            new SelectList(new myPrj.Models.DbContext().Tags, "ID", "TagName"))
    </td>        
    <td>
        <input type="button" onclick="$(this).parent().parent().remove();" 
            value="Remove" />
    </td>
</tr>

By calling this partial view in the create place view ajaxly, you can render some elements for each tag. Each line of elements contains a label, a DropDownList containing tags, and a remove button to simply remove the created elements.

In the create place view, you have a bare table which will contain those elements you create through the partial view:

<fieldset>
     <legend>Place Tags</legend>
     @Html.ValidationMessageFor(model => model.Tags)</label>
     <table id="tblTags"></table>                                        
     <input type="button" id="btnAddTag" value="Add new tag"/>
     <img id="imgSpinnerl" src="~/Images/indicator-blue.gif" style="display:none;" />
</fieldset>

and you have the following script to create a line of elements for each tag:

$(document).ready(function () {
    $("#btnAddTag").click(function () {
        $.ajax({
            url: "/Controller/GetPlaceTagRow/Tags",
            type: 'GET', dataType: 'json',
            success: function (data, textStatus, jqXHR) {
                $("#tblTags").append(jqXHR.responseText);
            },
            error: function (jqXHR, textStatus, errorThrown) {
                $("#tblTags").append(jqXHR.responseText);
            },
            beforeSend: function () { $("#imgSpinnerl").show(); },
            complete: function () { $("#imgSpinnerl").hide(); }
        });
    });
});

The action method GetPlaceTagRow is like the following:

public PartialViewResult GetPlaceTagRow(string id = "")
    {            
        ViewBag.ListName = id;
        return PartialView("_CoursePostPartial");
    }

and your done for the create... The whole solution for your question has many codes for views, partial views, controllers, ajax calls and model binding. I tried to just show you the way because I really can't to post all of them in this answer.

Hope that this answer be useful and lead the way for you.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.