Upload
others
View
3
Download
0
Embed Size (px)
Citation preview
Routing and Form ValidationEDAF90 WEB PROGRAMMING
PER ANDERSSON
Routing
• the browser history is part of the user experience• allows the user to navigate back to earlier visited pages• an entry in the history is added when the user
– navigates to a new page using a link– submits a form
• traditionally, this loads a new page from the server• when a new page is loaded, all JavaScript objects are lost• singel page web application prevents this using preventDefault() on all
relevant events• only updating the DOM will impact the user experience:
– can not navigate using the browser history (back button)– can not link to inner pages
EDAF90 routing and form validation 1
Routing Framework
• there is an API giving JavaScript direct access to the browser history• using it manually is tedious and error prone• let a router do the work for you• a router have two main features: link and route
npm install react-router-dom
EDAF90 routing and form validation 2
Link
Link component:• replace <a href="other-page.html"> tags when navigation within your
application• appears and behaves as a normal link:
– clicking on it will add an entry to the browser history– this will update the url field in the browser– the user can bookmark or copy any page in your application– no new page is fetched from the server– your JavaScript objects are untouched (preserve the application state)
• add styling of active link using:<NavLink to="/react"activeClassName="hurray">
EDAF90 routing and form validation 3
Link Example
import { Link } from ’react-router-dom’;menu = (<ul><li><Link to="/">Home</Link></li><li><Link to="/users">Users</Link></li><li><Link to="/contact">Contact</Link></li>
</ul>);
EDAF90 routing and form validation 4
Route
<Route>
• path - matches if the pattern is a prefix of the current browser url• use exact for a complete match (no trailing characters)• a <Route> with no path is always matched• specify content:
– component - renders a react component if the path matches– render - calls a JavaScript if the path matches, the function returns a react element
(JSX expression)– children - always rendered, a function returning a react element
EDAF90 routing and form validation 5
Route
import { Route } from ’react-router-dom’const routes = (<div><Route path="/" exact component={Home} /><Route path="/about"
render={_ => <h1>About the app</h1>}></div>);
EDAF90 routing and form validation 6
Switch
<Switch>
• renders the first <Route> that matches• any other <Route>s will not be rendered
import { Route, Switch } from ’react-router-dom’const routes = (<Switch><Route path="/" exact component={Home} /><Route path="/items" component={Items} /><Route component={PageNotFound} />
</Switch>);
EDAF90 routing and form validation 7
Path Parameters
the router pass data from the path to the component• specify parameters in the path using the syntax:name• props.match.params is an object containing all path parameters• or use the useParams() hook to get that object
const elem = <Route path="/item/:itemId" render={Items} />;
function Items(props) {let { itemId } = useParams();return <h1> Item {itemId} </h1>;
}
EDAF90 routing and form validation 8
Hooks
• introduced in react router 5.1• can only be used in function components (stateless)• can be used in any child of Route• useParams() - returns the url path parameters• useRouteMatch() - returns the path
EDAF90 routing and form validation 9
Hooksfunction Item() {
const { id } = useParams();return <p>Item {id}</p>;
}function App() {return (
<Router><Route path="item//id"><Item />
</Route></Router>
);}
EDAF90 routing and form validation 10
Nested Routes• <Route> are react components and can be nested• path is absolute• useRouteMatch() helps you build relative paths
function About() {let { path, url } = useRouteMatch();return (
<Switch><Route exact path={path} component={GeneralInfo} /><Route path={{path} + "/copyright"}
component={Copyright} /></Switch>);
);}
EDAF90 routing and form validation 11
Router• any web application starts with a html file index.html• the html file includes the react JavaScript code• all <Route>s must be inside a router
<BrowserRouter>
• http://domain.se/item/42
• to allow direct links: the server must return the main html file for all urls• node do this for you• apache can be configured with redirect
<HashRouter>
• http://domain.se/#/item/42
• compatible with all servers
EDAF90 routing and form validation 12
Form Validation
• user feedback is important• common feedback comes from incorrectly filled forms• takes a lot of time to implement• html 5 introduced built in form validation
EDAF90 routing and form validation 13
HTML 5 Form Validation
html form input attributes:• required
• minlength and maxlength• min and max• type: number, email, . . .• pattern a regexp
Any error prevents form submission
EDAF90 routing and form validation 14
HTML 5 Form Validation
CSS pseudo classes set by the browser• :valid
• :invalid
input:invalid {border: 2px dashed red;
}input:invalid:required {background-image: linear-gradient(to right, pink,
lightgreen);}.form-control:valid~.invalid-feedback {display: none;}
EDAF90 routing and form validation 15
Constraint Validation API
adds read only properties to form input elements• validationMessage
• validity an object containing more info rangeOverflow and valid• checkValidity()
• setCustomValidity(message) makes the field invalid
But, you can not style the error message
EDAF90 routing and form validation 16
Custom Form Validation
Today, form validation is based on the following principle:• use html 5 attributes to define requirements• <form novalidate> prevents browser from displaying error messages• validation is still carried out by the browser• you can rely on the element.validity object• use JavaScript for manage error messages: catch the submit event• error messages: show or hide normal html elements, e.g.<spam class="my-error-class">invalid email</span>
Frameworks can help you with the details.
EDAF90 routing and form validation 17
Bootstrap
Bootstrap can style forms and error messages:• <input type="email"class="form-control"required><div class="invalid-feedback">my message</div>
– style depends on tag and type– scopes :invalid and :valid styles to parent .was-validated class– formElement.classList.add("was-validated");
• must use novalidate on <form> for custom error messages
check out the bootstrap documentation:https://getbootstrap.com/docs/4.4/components/forms/
EDAF90 routing and form validation 18
Bootstrap example<form novalidate><div class="form-row"><div class="col-md-4 mb-3"><label for="field1">First name</label><input type="text" class="form-control" id="field1"
required><div class="valid-feedback">Looks good!</div></div><div class="col-md-4 mb-3"><label for="field2">Last name</label><input type="text" class="form-control" id="field2"
required><div class="invalid-feedback">please enter your name</div></div></div><button class="btn btn-primary" type="submit">Submit form</
button></form>
EDAF90 routing and form validation 19
Security
A note on security• server side form validation is mainly for giving users feedback• a malicious user can always interrupt the network communication• never trust data sent on the network (unless it is signed)• always do server side side data validation!• with client side validation, server side can focus on malicious code
EDAF90 routing and form validation 20