I am busy building a custom webpart with various textboxes and lookup fields. All of them are saving correctly apart from the lookup fields that allows for multiple selections. I dont have this problem with lookup fields that only allow for one value to be selected.
Below is the code for getting all the selected items in my checkboxlist, converting it to a multichoice value and assigning to my list[columnname]
try
{
SPFieldMultiChoiceValue _segmentchoices = new SPFieldMultiChoiceValue();
foreach (ListItem ls3 in _segment.Items)
{
if (ls3.Selected) _segmentchoices.Add(ls3.Value);
}
myItems["Segment"] = _segmentchoices;
myItems.Update();
}
catch (Exception ex) { _errorMessage += "||| Segment : " + ex.Message; }
The values list (_segmentchoices) is correctly created and looks like this : {;#1;#2;#3;#4;#5;#}
However when its saved it only saves values 1, 3, and 5.
My code is not generating an error, so I am at a loss at what could be wrong. Any ideas on what I need to look at? Am I going about it the wrong way?
Any assistance would be appreciated.
Thank you
I just realized you are talking about a multi-select lookup field. The format should be something like: 2;#Procedures;#3;#Systems;#7;#Services
The behavior you describe makes sense because it is probably interpreting ;#1;#2;#3;#4;#5;# like this: get the item in the lookup list with a lookupID of 1 (lookupValue is 2), lookupID of 3 (lookupValue is 4), and lookupID of 5 (lookupValue is empty)
Here is some code that you can use to update a multi-select choice field:
using (SPSite site = new SPSite(siteUrl))
{
using (SPWeb web = site.OpenWeb())
{
SPList list = web.Lists[listName];
SPListItem item = list.Items[0];
SPFieldLookupValueCollection spflvc = new SPFieldLookupValueCollection();
spflvc.Add(new SPFieldLookupValue(3, string.Empty));
spflvc.Add(new SPFieldLookupValue(7, string.Empty));
item["Keywords"] = spflvc;
item.Update();
}
}
The second parameter to SPFieldLookupValue doesn't seem to care if it is passed string.Empty which also might explain why it ignores them above.
Related
So I'm working on learning LINQ and was assigned to work with two .txt files and to join them.
So far I'm doing well, but I've reached a bit of an impasse with the display. I'm supposed to have the name display once and then the following cases that are closed have only the case information.
The issue I'm having is that the name keeps repeating after the dataset is listed in the ListView. I think there is something wrong with the LINQ statement or the way I'm going through the foreach loop. Here is the code for the main form below:
//Fills the lists by calling the methods from the DB classes
techs = TechnicianDB.GetTechnicians();
incidents = IncidentDB.GetIncidents();
//Creates a variable to use in the LINQ statements
var ClosedCases = from Incident in incidents
join Technician in techs
on Incident.TechID equals Technician.TechID
where Incident.DateClosed!= null
orderby Technician.Name, Incident.DateOpened descending
select new { Technician.Name, Incident.ProductCode, Incident.DateOpened, Incident.DateClosed, Incident.Title };
//variables to hold the technician name, and the integer to increment the listview
string techName = "";
int i = 0;
//foreach loop to pull the fields out of the lists and to display them in the required areas in the listview box
foreach (var Incident in ClosedCases)
{
foreach (var Technician in ClosedCases)
{
if (Technician.Name != techName)
{
lvClosedCases.Items.Add(Technician.Name);
techName = Technician.Name;
}
else
{
lvClosedCases.Items.Add("");
}
}
lvClosedCases.Items[i].SubItems.Add(Incident.ProductCode);
lvClosedCases.Items[i].SubItems.Add(Incident.DateOpened.ToString());
lvClosedCases.Items[i].SubItems.Add(Incident.DateClosed.ToString());
lvClosedCases.Items[i].SubItems.Add(Incident.Title);
i++;
}
And here is the result I get: Result
As can be seen by the bar on the right hand side, the list continues on for several more columns.
What am I missing here?
Thank you.
EDIT: Per request, here is what the results are supposed to look like:
The example I was given
Why you are iterating closed cases twice?
foreach (var Incident in ClosedCases)
{
foreach (var Technician in ClosedCases)
{
}
}
I have more than 15000 POCO elements stored in a Redis List. I'm using ServiceStack in order to save and get them. However, I'm not pleased about the response times that I have when I get them into a grid. As I read , it would be better to store these object in hash - but unfortunately I could not find any good example for my case :(
This is the method I use, in order to get them into my grid
public IEnumerable<BookingRequestGridViewModel> GetAll()
{
try
{
var redisManager = new RedisManagerPool(Global.RedisConnector);
using (var redis = redisManager.GetClient())
{
var redisEntities = redis.As<BookingRequestModel>();
var result =redisEntities.Lists["BookingRequests"].GetAll().Select(z=> new BookingRequestGridViewModel
{
CreatedDate =z.CreatedDate,
DropOffBranchName =z.DropOffBranch !=null ? z.DropOffBranch.Name : string.Empty,
DropOffDate =z.DropOffDate,
DropOffLocationName = z.DropOffLocation != null ? z.DropOffLocation.Name : string.Empty,
Id =z.Id.Value,
Number =z.Number,
PickupBranchName =z.PickUpBranch !=null ? z.PickUpBranch.Name :string.Empty,
PickUpDate =z.PickUpDate,
PickupLocationName = z.PickUpLocation != null ? z.PickUpLocation.Name : string.Empty
}).OrderBy(z=>z.Id);
return result;
}
}
catch (Exception ex)
{
return null;
}
}
Note that I use redisEntities.Lists["BookingRequests"].GetAll() which is causing performance issues (I would like to use just redisEntities.Lists["BookingRequests"] but I lose last updates from grid - after editing)
I would like to know if saving them into list is a good approach as for me it's very important to have a fast grid (I have now 1 second at paging which is huge).
Please, advice!
Firstly you should not create a new Redis Client Manager like RedisManagerPool instance each time, there should only be a singleton instance of RedisManagerPool in your App which all clients are resolved from.
But otherwise I would rethink your data access strategy, downloading 15K items in a batch is not an ideal strategy. You can create indexes by storing ids in Sets or you could store items in a sorted set with a value that you can page against like an incrementing id, e.g:
var redisEntities = redis.As<BookingRequestModel>();
var bookings = redisEntities.SortedSets["bookings"];
foreach (var item in new BookingRequestModel[0])
{
redisEntities.AddItemToSortedSet(bookings, item, item.Id);
}
That way you will be able to fetch them in batches, e.g:
var batch = bookings.GetRangeByLowestScore(fromId, toId, skip, take);
This is a part of the code that i was trying to use to get the respective elements, but it keeps giving me the following error:
System.Collections.ObjectModel.ReadOnlyCollection`1[OpenQA.Selenium.IWebElement]or
others identical
This is also shown in a datagridview, in her rows.
IList<IWebElement> ruas = Gdriver.FindElements(By.ClassName("search-title"));
String[] AllText = new String[ruas.Count];
int i = 0;
foreach (IWebElement element in ruas)
{
AllText[i++] = element.Text;
table.Rows.Add(ruas);
}
First thing is: as far as I understand the elements you are talking about are not contained in table. Its a list: <ul class="list-unstyled list-inline">... (considering the comment you left with site link)
If you want to find those elements you can use the code below:
var elements = driver.FindElements(By.CssSelector("ul.list-inline > li > a"));
// Here you can iterate though links and do whatever you want with them
foreach (var element in elements)
{
Console.WriteLine(element.Text);
}
// Here is the collection of links texts
var linkNames = elements.Select(e => e.Text).ToList();
Considering the error you get, I may assume that you are using DataGridView for storing collected data, which is terribly incorrect. DataGridView is used for viewing data in MVC application. There is no standard Selenium class for storing table data. There are multiple approaches for this, but I can't suggest you any because I don't know your what you are trying to achieve.
Here is how i answered my own question:
IList<string> all = new List<string>();
foreach (var element in Gdriver.FindElements(By.ClassName("search-title")))
{
all.Add(element.Text);
table.Rows.Add(element.Text);
}
I'm building a form, where the number of questions, or inputs on the form varies depending on the value in a database.Each input on the form is a radio type. The name of the tags are dynamic and are loaded from the database using #db.row.questionID which would look something like: <span name=#id> and equal a value of 1 through whatever queries were requested.
My issue is, i wrote the form using post, and i want to submit the values back into a separate database, but i dont know how to request multiple values, that changes dynamically based on query.
Sample code i wrote, it doesnt give me any errors, but it doesnt give me any results either.
foreach(var prow in poll){
var Question = prow.PollId;
if (Request.Form["#prow.PollId"] == "A") {
int AnsA = row.ResultsA;
AnsA = AnsA + 1;
db.Execute("UPDATE Results SET ResultsA=#0 WHERE ResultsId=#1", AnsA, Question);
}
i have also tried:
if (Request["prow.PollId"] == "B") {
int AnsB = row.ResultsB;
AnsB += 1;
db.Execute("UPDATE Results SET ResultsB=#0 WHERE ResultsId=#1", AnsB, prow.PollId);
}
Do you want to get value in form with dynamic inputs? If yes, you can try this:
NameValueCollection nvc = Request.Form;
foreach (var item in Request.Form.AllKeys)
{
//do something you want.
// Examble : if(item == "A")// item will return name of input
// Note: nvc[item] return value of input
}
Update:
Request.Form.AllKeys will return all of input name in form.
We use foreach to lopp through colections of input name.
Use nvc[item] or Request.Form[item] to get value of input.
You can read this article :c#: get values posted from a form
This section simply reads from an excel spreadsheet. This part works fine with no performance issues.
IEnumerable<ImportViewModel> so=data.Select(row=>new ImportViewModel{
PersonId=(row.Field<string>("person_id")),
ValidationResult = ""
}).ToList();
Before I pass to a View I want to set ValidationResult so I have this piece of code. If I comment this out the model is passed to the view quickly. When I use the foreach it will take over a minute. If I hardcode a value for item.PersonId then it runs quickly. I know I'm doing something wrong, just not sure where to start and what the best practice is that I should be following.
foreach (var item in so)
{
if (db.Entity.Any(w => w.ID == item.PersonId))
{
item.ValidationResult = "Successful";
}
else
{
item.ValidationResult = "Error: ";
}
}
return View(so.ToList());
You are now performing a database call per item in your list. This is really hard on your database and thus your performance. Try to itterate trough your excel result, gather all users and select them in one query. Make a list from this query result (else the query call is performed every time you access the list). Then perform a match between the result list and your excel.
You need to do something like this :
var ids = so.Select(i=>i.PersonId).Distinct().ToList();
// Hitting Database just for this time to get all Users Ids
var usersIds = db.Entity.Where(u=>ids.Contains(u.ID)).Select(u=>u.ID).ToList();
foreach (var item in so)
{
if (usersIds.Contains(item.PersonId))
{
item.ValidationResult = "Successful";
}
else
{
item.ValidationResult = "Error: ";
}
}
return View(so.ToList());