I read from Jmock's homepage about matchers, and at the very top there was an example about string matchers. I didn't understand because, according to the example, matching a string would be as easy as writing import static org.hamcrest.Matchers.*; and then using the stringContains function, but that doesn't work on my implementation.
All I want to do is
new Expectations() {{
mockedType.someFunction(with( **match string here** ) );
}};
new Expectations() {{
allowing(mockedType).someFunction("My String"); when ... ; will ... ; then ...
}};
Must be working
Related
I'm doing my first steps with Newtonsoft Json parser, but there are very fex examples on VB.net apperently. I just want to parse a string, and then I want to be able to loop throught the different list
This is my code :
Dim JSON As String
Dim values As Newtonsoft.Json.Linq.JObject
JSON = "{'mailadresses': { 'List1':{'Stefaan Somers': 'JoskeVermeulen#gmail.com', 'Markske': 'mdtre#gmail.com' }, 'List2':{'Stefaan XSomers': 'Test#gmail.com', 'xMarkske': 'mdrmdtre#gmail.com' }}"
values = JObject.Parse(JSON)
It directly gives me the error when running :
Unexpected end of content while loading JObject. Path 'mailadresses', line 1, position 221.
Any idea also on how to loop through the different elements. I don't want to cast to a custom class, as described in many samples
Your json isnt valid according to jsonlint.
try this instead:
{
"mailadresses": {
"List1": {
"StefaanSomers": "JoskeVermeulen#gmail.com",
"Markske": "mdtre#gmail.com"
},
"List2": {
"StefaanXSomers": "Test#gmail.com",
"xMarkske": "mdrmdtre#gmail.com"
}
}
}
I have an ASP.NET page which takes a number of parameters in the query string:
search.aspx?q=123&source=WebSearch
This would display the first page of search results. Now within the rendering of that page, I want to display a set of links that allow the user to jump to different pages within the search results. I can do this simply by append &page=1 or &page=2 etc.
Where it gets complicated is that I want to preserve the input query string from the original page for every parameter except the one that I'm trying to change. There may be other parameters in the url used by other components and the value I'm trying to replace may or may not already be defined:
search.aspx?q=123&source=WebSearch&page=1&Theme=Blue
In this case to generate a link to the next page of results, I want to change page=1 to page=2 while leaving the rest of the query string unchanged.
Is there a builtin way to do this, or do I need to do all of the string parsing/recombining manually?
You can't modify the QueryString directly as it is readonly. You will need to get the values, modify them, then put them back together. Try this:
var nameValues = HttpUtility.ParseQueryString(Request.QueryString.ToString());
nameValues.Set("page", "2");
string url = Request.Url.AbsolutePath;
string updatedQueryString = "?" + nameValues.ToString();
Response.Redirect(url + updatedQueryString);
The ParseQueryString method returns a NameValueCollection (actually it really returns a HttpValueCollection which encodes the results, as I mention in an answer to another question). You can then use the Set method to update a value. You can also use the Add method to add a new one, or Remove to remove a value. Finally, calling ToString() on the name NameValueCollection returns the name value pairs in a name1=value1&name2=value2 querystring ready format. Once you have that append it to the URL and redirect.
Alternately, you can add a new key, or modify an existing one, using the indexer:
nameValues["temp"] = "hello!"; // add "temp" if it didn't exist
nameValues["temp"] = "hello, world!"; // overwrite "temp"
nameValues.Remove("temp"); // can't remove via indexer
You may need to add a using System.Collections.Specialized; to make use of the NameValueCollection class.
You can do this without all the overhead of redirection (which is not inconsiderable). My personal preference is to work with a NameValueCollection which a querystring really is, but using reflection:
// reflect to readonly property
PropertyInfo isReadOnly = typeof(System.Collections.Specialized.NameValueCollection).GetProperty("IsReadOnly", BindingFlags.Instance | BindingFlags.NonPublic);
// make collection editable
isReadOnly.SetValue(this.Request.QueryString, false, null);
// remove
this.Request.QueryString.Remove("foo");
// modify
this.Request.QueryString.Set("bar", "123");
// make collection readonly again
isReadOnly.SetValue(this.Request.QueryString, true, null);
Using this QueryStringBuilder helper class, you can grab the current QueryString and call the Add method to change an existing key/value pair...
//before: "?id=123&page=1&sessionId=ABC"
string newQueryString = QueryString.Current.Add("page", "2");
//after: "?id=123&page=2&sessionId=ABC"
Use the URIBuilder Specifically the link textQuery property
I believe that does what you need.
This is pretty arbitrary, in .NET Core at least. And it all boils down to asp-all-route-data
Consider the following trivial example (taken from the "paginator" view model I use in virtually every project):
public class SomeViewModel
{
public Dictionary<string, string> NextPageLink(IQueryCollection query)
{
/*
* NOTE: how you derive the "2" is fully up to you
*/
return ParseQueryCollection(query, "page", "2");
}
Dictionary<string, string> ParseQueryCollection(IQueryCollection query, string replacementKey, string replacementValue)
{
var dict = new Dictionary<string, string>()
{
{ replacementKey, replacementValue }
};
foreach (var q in query)
{
if (!string.Equals(q.Key, replacementKey, StringComparison.OrdinalIgnoreCase))
{
dict.Add(q.Key, q.Value);
}
}
return dict;
}
}
Then to use in your view, simply pass the method the current request query collection from Context.Request:
<a asp-all-route-data="#Model.NextPageLink(Context.Request.Query)">Next</a>
If I have the following code:
var value : String = StringUtil.substitute("The value {0} requested is {1}", user, value);
How can I use the variable name instead of using {0} and {1} in the code.
Please advice. Thanks.
Edit:
The above code is quoted from http://www.rialvalue.com/blog/2010/05/10/string-templating-in-flex/.
It says that "Also note that we’re substituting the parameters using the order, it’d would fairly easy to do a named-parameter subsitution instead (i.e. using tokens like ${var1})". Therefore, I think it may be very easy to do that, but I don't know how to do.
Looks like it's not possible. And kind of makes sense that it allows zero based ints only, since you're passing a variable number of parameters that you're not identifying (except for their relative position in the params list).
Here's a piece of code that will replace tokens by name:
public static function replacePlaceholders(input:String,replacementMap:Object):String {
// '${', followed by any char except '}', ended by '}'
return input.replace(/\${([^}]*)}/g,function():String {
return replaceEntities(arguments,replacementMap);
});
}
private static function replaceEntities(regExpArgs:Array,map:Object):String {
var entity:String = String(regExpArgs[0]);
var entityBody:String = String(regExpArgs[1]);
return (map[entityBody]) ? map[entityBody] : entity;
}
Use:
var test:String = "Hello there ${name}, how is the ${noun} today?";
var replacementMap:Object = {
name : "YOUR_NAME_HERE",
noun : "YOUR_NOUN_HERE"
};
trace(StringUtils.replacePlaceholders(test,replacementMap));
The format I'm using for the placeholders is ${placeholdername}, since it's safer, I think. But if you want to remove the dollar sign, change the regexp accordingly.
I'm generating emails based off embedded NVelocity templates and would like to do something with dynamically included sections. So my embedded resources are something like this:
DigestMail.vm
_Document.vm
_ActionItem.vm
_Event.vm
My email routine will get a list of objects and will pass each of these along with the proper view to DigestMail.vm:
public struct ItemAndView
{
public string View;
public object Item;
}
private void GenerateWeeklyEmail(INewItems[] newestItems)
{
IList<ItemAndView> itemAndViews = new List<ItemAndView>();
foreach (var item in newestItems)
{
itemAndViews.Add(new ItemAndView
{
View = string.Format("MyAssembly.MailTemplates._{0}.vm", item.GetType().Name),
Item = item
});
}
var context = new Dictionary<string, object>();
context["Recipient"] = _user;
context["Items"] = itemAndViews;
string mailBody = _templater.Merge("MyAssembly.MailTemplates.DigestMail.vm", context);
}
And in my DigestMail.vm template I've got something like this:
#foreach($Item in $Items)
====================================================================
#parse($Item.viewname)
#end
But it's unable to #parse when given the path to an embedded resource like this. Is there any way I can tell it to parse each of these embedded templates?
Hey Jake, is .viewname a property? I'm not seeing you setting it in your code, how about you use the following:
#foreach($Item in $Items)
====================================================================
$Item.viewname
#end
I don't know why you're parsing the $Item.viename rather than just using the above? I'm suggesting this as I've just never needed to parse anything!
Please refer to this post where we've discussed the generation of templates.
Hope this helps!
I have a function that has this line:
var returnString:String = items[0].#month;
#month is an attibute on an XML node like so:
<xmlnode month="JAN"/>
OK but I need to abstract the attribute name so I can pass a string to the function and get the contents of the attribute with the name matching the string I passed. So for example If I call the function like this function("stone") it returns items[0].#stone. I hope this is clear.
Does anyone know how to do what I am after?
Thanks.
You'll want to use attribute('stone') rather than #stone, its the same thing, #stone is just a shorthand way of writing it.
You can write this as:
var attrName:String = "month";
return items[0].#[ attrName ];
not only that, but if you ever want to assign a value to an attribute using a variable for the attribute name, you can do this (although it is not documented) like so:
public function setAttr(obj:XML, attrName:String, value:String):void{
obj.#[attrName] = value;
}