Why does passing parameters via Link react-router not work? React-Router-v6 - react-router

How I am calling Link
<Link to={{ pathname: row.route, partname: "test" }} className='nav-links'>
<Button variant="contained">Choose {row.name}</Button>
</Link>
How I am trying to access it:
export default function Products() {
const location = useLocation()
const partname = location.state?.partname
console.log("partname: " + partname)
But partname is always null even though I am passing in partname = "test".
I am pretty new to React and it seems like this is the standard way to pass in arguments to functions components. Thanks in advance! \
Using:
"react-router-dom": "^6.0.1",

Hmm it seems like this works for v6:
<Link to={row.route} state={{partname: "test"}}><Button variant="contained">Choose {row.name}</Button></Link>

Related

React: Skip row if json parent tag don't exist

I am in the following situation and have the following problems.
I am developing an application that reads data from a .json file. I store this data in rows. Now the .json files can be different and therefore I have to cover every case (there are many cases). If a tag is not present in the .json, this row should not be displayed.
Now it can happen that I have covered a case which searches for data.test.person but data.test is not present in the JSON.
A case could look like this:
<TestAntragsdatenAbschnitt
title={"Test"}
value={data.test}>
<TestAntragsdatenRow
label1={"Person"}
value1={data.test.person}
/>
</TestAntragsdatenAbschnitt>
This is my component.
export default class TestAntragsdatenAbschnitt extends React.Component {
value;
title;
render() {
this.value = this.props.value;
this.title = this.props.title;
return (
<>
<h4 className={"antragsdatenAbschnitt"}>
{checkAbschnitt(this.title, this.value)}
</h4>
{this.value != null &&
this.props.children
}
</>
);
}
}
With the query this.value != null && I have tried to work around the error.
The error I get: TypeError: Cannot read property 'person' of undefined
My question now is, how can I query JSON tags if they exist, if so the rows should be checked. If not all rows with this tag should be skipped.
Object.keys(data).includes('test')
can be a way of checking if json object has the property.
There are a lot of other ways as well. You can also try:
value1={data.test ? data.test.person : 'error'}
kind of approach for safe null-checking
There are a couple of things wrong with your code, but let's try to unpack everything:
You're passing two props, title and value to your component named TestAntragsdatenAbschnitt. This you should receive in props, and therefore there's no need for you to store them in fields (this.value = this.props.value) for example.
Rather, just do this in the render function:
const {title, value, children} = this.props;
And now you don't need to use this.title and this.value, but just title and value.
OK we got that out of the way, now let's figure out why your optional key isn't working:
Now you should be rendering your children like this:
{children}
Now you need to conditionally render particular rows, and this shouldn't be done here in this component at all. This should be done in the component that's rendering TestAntragsdatenAbschnitt (first component you wrote in the post).
So you'd do something like this:
<TestAntragsdatenAbschnitt
title={"Test"}
value={data.test}>
{data && data.test && data.test.person ? (
<TestAntragsdatenRow
label1={"Person"}
value1={data.test.person}
/>
) : (
<p>data.test.person is not valid</p>
)}
</TestAntragsdatenAbschnitt>
As you can see, I check with the ternary operator if data.test.person is not null, if it isn't then just render the row, if not then just do something else you'd like.
You could do this in other component, but this way it's way cleaner in my opinion.

How to render nested routes with multiple optional params and path placeholders?

I've been trying to use react-router to define a series of nested components/routes w/ optional params, but also separated by path placeholders.
i.e.
/list
/list/1
/list/items
/list/1/items
/list/1/items/1
I would assume the two <Route> paths would be something like:
/list/:listId?
and
`${match.url}`/items/:itemId?`
But alas.. "items" always ends up being accepted as the listId param, and therefore, the sub-routing for /items never matches.
I have a generic example I've coded here (doesn't accomplish a solution): https://stackblitz.com/edit/nesting-w-optional-params-react-router
I see examples all over the internet for /root/:id1?/:id2? but nothing for what I'm trying to do where I have a placeholder between the params: /root/:id1/placeholder/:id2.
Is this possible to do w/ react-router v4+ ??
Figured out a solution utilizing RR's children pattern, to always render the nested route/component, but then inside the component use path-to-regexp directly to do route matching and to grab relevant route params from props.location.pathname.
Relevant bit of code:
render() {
const pathRe = new PathToRegexp('/foo/:fooId?/bar/:barId?')
const match = pathRe.match(this.props.location.pathname)
if (!match) {
return null
}
const barId = (this.props.match && this.props.match.params.barId) || match.barId
return <h1>Bar <em>{barId}</em></h1>
}
https://stackblitz.com/edit/nesting-w-optional-params-react-router-solution

Undefined class constant 'TYPE_LIST' yii2-widget-depdrop

I'm using yii2 in local server but I face error like this
Undefined class constant 'TYPE_LIST'
...
...
'type' => DepDrop::TYPE_LIST
...
...
So, I check vendor/kartik-v/yii2-widget-depdrop/DepDrop.php
There is no const TYPE_LIST but when I check thus file in production server there is const TYPE_LIST = 3
Package version is yii2-widget-depdrop 1.0.4 for both server, production and local
But when I check official package repo https://github.com/kartik-v/yii2-widget-depdrop/blob/master/DepDrop.php
There is no const TYPE_LIST
How I can fix this error?
Thanks in advance
You are looking to the wrong component
for depdrop the type is
type: int the type of dropdown list to be generated. Should be one of
the following values:
1 or DepDrop::TYPE_DEFAULT: render a default HTML select using
\yii\helpers\Html::dropDownList.
2 or DepDrop::TYPE_SELECT2: render advanced Select2 using
\kartik\widgets\Select2 widget.
If not set the type will default to 1 or DepDrop::TYPE_DEFAULT.
for sortable type is
The Sortable widget allows you to configure the following properties:
type: string, the type of the sortable widget. Defaults to
Sortable::TYPE_LIST. Should be one of
Sortable::TYPE_LIST or list
Sortable::TYPE_GRID or grid
http://demos.krajee.com/sortable
http://demos.krajee.com/widget-details/depdrop

React - How to iterate over dictionary in render method using JSX?

I'm learning React and have set up a small test app that makes an Ajax call that returns a JSON object that I want to iterate over in the return method of my component. I've tried everything I can think of and have googled this, but like an hour later I'm still stumped.
Here is what I have...
render() {
const { vals } = this.state;
return (
<div>
{/* note that this correctly outputs the value of vals[key]: {vals['key']} */}
Object.keys({vals}).map((key, index) => (
<p key={index}> this is my key {key} and this is my value {vals[{key}]} </p>
))
</div>
)
}
What am I doing wrong here? Any recommendations on a good reference for ES6/JSX? I've been struggling with simple things, with no good way to look up this info.
{vals} extracts out the vals property from an object. Hence Object.keys({vals}) is incorrect as vals is already an object. Likewise, it should be {vals[key]} instead of {vals[{key}]}.
render(){
const {vals} = this.state; // Essentially does: const vals = this.state.vals;
return (
<div>
{
Object.keys(vals).map((key, index) => (
<p key={index}> this is my key {key} and this is my value {vals[key]}</p>
))
}
</div>
)
}
If vals is an object containing { a: 1, b: 2}, Object.keys(vals) will get you ['a', 'b'] and in the first iteration of the map, key will be 'a' and to access the value, do vals[key] which is essentially vals['a'] => 1.
I think you are confused by the Object destructuring syntax. It's really quite simple as it's just syntactic sugar over ES5 JavaScript (most ES6 is just sugar). Have a read at MDN's docs on Destructuring assignment to understand it better.

razor URL actionlink

I am trying to create this URL link:
mysite.com/Vote/2/Learn-to-code
Where
area = vote,
id = 2,
topicURL = Learn-to-code
In my routing, I have this to handle this URL pattern:
context.MapRoute(
"Topic",
"Vote/{id}/{topicURL}",
new { controller = "Topic", action = "TopicAnswers" },
new[] { "eus.UI.Areas.Vote.Controllers"}
);
But I am having trouble generating the URL link. Here's my attempt:
#Html.ActionLink("ViewBag.TopicTitle", "TopicAnswers", new { area = "Vote", controller = "Topic", id = ViewBag.TopicId, topicURL = #ViewBag.TopicURL })
First question is: How do I use ViewBag.TopicTitle? If I remove the quotes, it gives red squiggly error. I put the quotes in just so I could run the app to see what URL this generates.
It generates a monster URL.
mysite.com/Vote/Topic/TopicAnswers/2?url=Learn-to-code
However, the URL actually works. But I would really like to create my short and clean looking URL.
mysite.com/Vote/2/Learn-to-code
Any tips greatly appreciated, gracias.
Ok, I did this and it works. This is so simple to read and understand.
#ViewBag.TopicTitle
Is there any good reason why I should attempt to use #Html.ActionLink(...). That just feels like spaghetti.
For starters, why do they place the parameters ("text", action, controller) in this order? That is such a twisty path. This is far more natural to think of:
(controller, action, "text") ... is it not?