AngularJS + UI Router: route with variable parameter and specific value handling (exceptions) - angularjs

There is probably a better way to refer to this issue but I can't think of it at the moment.
I'm posting this to hopefully help anyone who ends up having this situation pop up. I couldn't find an answer anywhere when I was trying to figure this out.
The issue:
You have a state with one or more variable parameters.
Ex: /arg1/arg2/:var1
But there are exceptions where :var1 has a specific deviation from the norm you establish with that state .
In other words, :var1 can be anything except "foo". If :var1 == foo (/arg1/arg2/foo), then you need to handle that state differently.
My specific case for this was with a state url like: /arg1/arg2/arg3/:var1/arg4/:var2/:var3 where :var3 had an exception if it was "exact" (/arg1/arg2/arg3/:var1/arg4/:var2/exact).

The solution is simple but may not be completely (or immediately) obvious.
Place the exception state above the fully variable state.
In other words:
.state('stateexception',{url:'/arg1/arg2/foo'})
.state('fullvarstate',{url:'/arg1/arg2/:var1'})

Related

Reactjs, strange behavior on checking state value (again)

Ok, there is something I don't understand again:
onDateChange(child, performUpdate){
console.log("child", child, child.state);
}
As you can see, from the debugeur, the state has some value. But when I try to access them, they act like if they where not initialized. Like if the setState wasn't an atomic operation after all...
Actually I don't have any idea as it seems counter intuitive.
Can someone help me to get my data from the callback. Every operation in js/reactjs act differently from what it is expected.
Is that because the 'state' property is in another field and duplicated? I can't find any logical reason for this strange behavior.
edit:
So it appear that setState is asynchronuous. And worst part, non atomic operation. This is kind of strange they don't speak of that in the documentation (instead they said to not use state directly but by method call. Why? Because they do the change in another thread without telling the client!!!).
So this is how you have concurrency problem like I had.
Is there a clean approach for this kind of problem? Like a callback on setState method when all the operation are done (some people use delay or inline function, which absolutly don't correct the problem ).
To resolve my issue, I had to use a proxy pattern where there is the datastructure independantly from the view who display it, and act as if it was the same object. So that the controller don't have to deal with all this 'background' threaded operation mess. (Note: the datastructure is not a model, but a readonly object).

force $state.reload with a start from state

I have the following states: 'home.person','home.person.house'
I'm in 'home.person.house' and want to hard reload state stating from 'home.person'. According to https://github.com/angular-ui/ui-router/pull/1809, I can pass as a parameter the start state from which the reload will start. So, I have the following line:
$state.reload('home.person');
However, the reload doesn't occur even thought everything in ui-route seems to work fine (debugged it). The resolve function of state 'home.person' wasn't called. Are there any suggestions why I'm not getting the result I wish for?
You can try using this :
$state.go("home.person",{reload:true});
It would be good if you could share the parent and child state codes. It's difficult to provide a solution without much reference.

How to configure angular ui-router state that will match any and all present query parameters?

The Problem:
I'd like a single ui-router state to match the following urls:
#/.../update?id
#/.../update?username
#/.../update?customerId&sandwichId
If/when the 'update' state is active (it's a routed component), the component's controller knows enough to expect which params will be there (via a provided array of Strings that should/will match whatever query params are in fact present).
Current Solutions (none of which I'm 100% happy with)
I could just leave the url at '#/.../update' with the implicit understanding that I cannot navigate to that url from anywhere but it's parent state, and just pass in its primary key fields as a component binding. The drawback obviously being if I just type the URL in my browser, it will not have enough information to load.
As per an example I found here, I defined my 'update' state with single query parameter: pkKeys. I then define pkKeys upon my state transition to be the entire query parameter string I desire. This effectively achieves what I am looking for. However, typing this just doesn't feel right:
#/.../update?pkKeys=username=test
Moreover, it looks ugly on the more complicated situations:
#/.../update?pkKeys=customerId%3D3ae2e6eb-3bf7-42f8-a09c-9c690c8dbe15%26sandwichId%3D2cb6d513-06a3-4aa4-93bb-e53d279d95cb
Ideal Target State
Ideally, I'm looking for a way to configure my state in a way that matches the above patterns of urls. I did not have much success with $location service, but something tells me that has something to do with it. It appeared to me that $location.search() was cleared whenever $state.go( ... ) was invoked.
Thanks for any help in advance! Happy to elaborate on anything that might not be clear. It's a rather unique problem set I find myself in here...
On Further Research
For reference, I'm using Angular UI Router 1.x. I have found they have the notion of dynamic parameters, which seems to nearly solve the problem I am encountering (see the GitHub issue for this change). However, where this fails me is the state configuration still expects you to list the dynamic parameter's name. As my query param names are data-driven, the set of names is not a finite set. So I need dynamic parameters...with dynamic names.

ReactJS - How to Prevent ContextTypes from being altered

I have two context types: (1) productsContexts & (2) rangeContext.
rangeContext is nothing more than preset ranges from a json file so as to group the products according to each respective range.
Below is an illustration of a side-box component that groups products
according to those preset ranges and it also illustrates the problem:
The first visit to that page, everything works fine, but click off and then re-visit the page and the previous data remains and then doubles itself, 3rd time, it is triple, and so on.
I did nothing with the rangeContext data but pass it along to a local variable for mapping data manipulation. I did not save anything to the context itself.
Here is what I have tried to do to solve this problem; all have failed:
I passed the rangeContext to state first, then on componentWillUnmount, I initialized state.
I Object.assign() the rangeContext to the local variable instead of directly passing the context to the local variable.
I took the context completely out of this component and used it in it's parent, and passed it to this component as props.
Nothing is working. While the hard data does not change, the range component never gets initialized on unmount and revisiting the page just carries forward what was in the range in the last visit and adds to it.
I know I probably did not do a great job explaining, but I know the problem is related to the context and I sure do not want to hit the database again, as I already did that for an earlier component.
Does anyone recognize the problem and have a solution?
Thanks
UPDATE:
I moved contextTypes for ranges out of the side-box component.
Using redux flux, I dispatched for the range-actions in side-box's parent and passed the ranges to side-box as props. The problem went away, but I am not happy. I need someone to tell me why this is the right things to do, as ...
I had already called range-actions in a previous component, so why not put it in contextTypes instead of calling redux again?
Where as I only had 3 lines of code on side box, I have the same amount of code lines since now I am calling propTypes, but now I also have
MORE LINES of code in the parent calling redux, something I had already done for the range data in a previous component.
I would greatly appreciate someone telling me if I am still doing this
all wrong, or why it is right I had to add 26 more REDUNDANT lines of
code calling redux flux?

Omniture Site Catalyst eVars and Props interchangable

I am studying Omniture/Site Catalyst on my own and have the following query:
Scenario where eVars can be used as a props variable.
Scenario where props can be used as a eVars variable.
I have a basic understanding of eVars and Props and as per my thinking the 2nd scenario is invalid and we can't use props in place of eVars.
Is there any scenario where eVars can be used as a props variable.
Props and eVars are only really interchangeable if you're looking to only record the actual value of something. They are pretty much different and not interchangeable in most other aspects.
One major thing a prop can do that an eVar can't is that you can enable pathing on a prop but not an eVar. But also, they have a handful of mutually exclusive items they can be correlated/broken down with, as well as some mutually exclusive available metrics.
Also, one or the other may be better for segmenting, depending on what you are actually trying to do.
Here is a link that gives more details:
http://helpx.adobe.com/analytics/kb/compare-props-evars.html
One thing to note that is out of date on that page is that you can now enable pathing on a prop yourself.
Scenario where eVars can be used as a props variable-When you expire evar on hit then it act as prop
Scenario where props can be used as a eVars variable-Only when you are interested to know Instances
Props have one value per page, eVars have one value per session [1]. You use props when you want to see how a value changes from page to page (pathing), you use eVars when you are interested in the value that was set last in the session (i.e. to identify an internal campaign).
Plus, what Crayon Violent said.
[1] Actually you can set different conditions at which eVars expire, so they might have different values in one session. Still, usually a new value overwrites the previous one in en eVars (hence no pathing for eVars).
Another way to look at it from a reporting aspect is props will tell you where users are going while eVars also let you know where they're coming from. We'll set an eVar on a directory page and not on the detail page - in the reports, though, you'll see that eVar against those detail pages...which can tell you which directory page (or other) the user came from (or...converted from, hence the idea of a conversion variable). The synonymous prop on the other hand only records visits to that directory page (just a traffic variable).

Resources