* chore: rename APIs and Microservices to include "Backend" (#42515) * fix typo * fix typo * undo change * Corrected grammar mistake Corrected a grammar mistake by removing a comma. * change APIs and Microservices cert title * update title * Change APIs and Microservices certi title * Update translations.json * update title * feat(curriculum): rename apis and microservices cert * rename folder structure * rename certificate * rename learn Markdown * apis-and-microservices -> back-end-development-and-apis * update backend meta * update i18n langs and cypress test Co-authored-by: Shaun Hamilton <shauhami020@gmail.com> * fix: add development to front-end libraries (#42512) * fix: added-the-word-Development-to-front-end-libraries * fix/added-the-word-Development-to-front-end-libraries * fix/added-word-development-to-front-end-libraries-in-other-related-files * fix/added-the-word-Development-to-front-end-and-all-related-files * fix/removed-typos-from-last-commit-in-index.md * fix/reverted-changes-that-i-made-to-dependecies * fix/removed xvfg * fix/reverted changes that i made to package.json * remove unwanted changes * front-end-development-libraries changes * rename backend certSlug and README * update i18n folder names and keys * test: add legacy path redirect tests This uses serve.json from the client-config repo, since we currently use that in production * fix: create public dir before moving serve.json * fix: add missing script * refactor: collect redirect tests * test: convert to cy.location for stricter tests * rename certificate folder to 00-certificates * change crowdin config to recognise new certificates location * allow translations to be used Co-authored-by: Nicholas Carrigan (he/him) <nhcarrigan@gmail.com> * add forwards slashes to path redirects * fix cypress path tests again * plese cypress * fix: test different challenge Okay so I literally have no idea why this one particular challenge fails in Cypress Firefox ONLY. Tom and I paired and spun a full build instance and confirmed in Firefox the page loads and redirects as expected. Changing to another bootstrap challenge passes Cypress firefox locally. Absolutely boggled by this. AAAAAAAAAAAAAAA * fix: separate the test Okay apparently the test does not work unless we separate it into a different `it` statement. >:( >:( >:( >:( Co-authored-by: Sujal Gupta <55016909+heysujal@users.noreply.github.com> Co-authored-by: Noor Fakhry <65724923+NoorFakhry@users.noreply.github.com> Co-authored-by: Oliver Eyton-Williams <ojeytonwilliams@gmail.com> Co-authored-by: Nicholas Carrigan (he/him) <nhcarrigan@gmail.com>
		
			
				
	
	
		
			137 lines
		
	
	
		
			4.2 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
			
		
		
	
	
			137 lines
		
	
	
		
			4.2 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
| ---
 | |
| id: 5a24c314108439a4d4036174
 | |
| title: 将 this 绑定到 Class 方法上
 | |
| challengeType: 6
 | |
| forumTopicId: 301379
 | |
| dashedName: bind-this-to-a-class-method
 | |
| ---
 | |
| 
 | |
| # --description--
 | |
| 
 | |
| 除了设置和更新 `state` 之外,还可以为组件类定义方法。 类方法通常需要使用 `this` 关键字,以便它可以访问方法中类的属性(例如 `state` 和 `props`)。 有几种方法可以让类方法访问 `this`。
 | |
| 
 | |
| 一种常见的方法是在构造函数中显式地绑定 `this`,这样当组件初始化时,`this` 就会绑定到类方法。 你可能已经注意到上一个挑战在构造函数中的 `handleClick` 方法使用了 `this.handleClick = this.handleClick.bind(this)`。 然后,当在类方法中调用像 `this.setState()` 这样的函数时,`this` 指的是这个类,而不是 `undefined`。
 | |
| 
 | |
| **注意:** `this`关键字是 JavaScript 中最令人困惑的方面之一,但它在 React 中扮演着重要的角色。 虽然它的行为在这里是完全正常的,但是这些课程并不深入研究`this`,所以如果以上内容令你感到困惑,请参考其他课程!
 | |
| 
 | |
| # --instructions--
 | |
| 
 | |
| 代码编辑器有一个带有 `state` 的组件,用于跟踪项目计数。 它还有一个方法,允许设置文本为 `You clicked!`。 但是,该方法不起作用,因为它使用了未定义的 `this` 关键字。 可以通过将 `this` 显式绑定到组件构造函数中的 `handleClick()`方法来修复它。
 | |
| 
 | |
| 接下来,向 render 方法中的 `button` 元素添加一个单击处理程序。 当按钮接收到单击事件时,它应该触发 `handleClick()` 方法。 记住,传递给 `onClick` 处理程序的方法需要使用花括号,因为它应该直接被解释为 JavaScript。
 | |
| 
 | |
| 完成上述步骤后,可以单击按钮并看到 `You clicked!`。
 | |
| 
 | |
| # --hints--
 | |
| 
 | |
| `MyComponent` 应返回 `div` 元素,该元素按顺序包含两个元素,一个按钮和一个 `h1` 元素。
 | |
| 
 | |
| ```js
 | |
| assert(
 | |
|   Enzyme.mount(React.createElement(MyComponent)).find('div').length === 1 &&
 | |
|     Enzyme.mount(React.createElement(MyComponent))
 | |
|       .find('div')
 | |
|       .childAt(0)
 | |
|       .type() === 'button' &&
 | |
|     Enzyme.mount(React.createElement(MyComponent))
 | |
|       .find('div')
 | |
|       .childAt(1)
 | |
|       .type() === 'h1'
 | |
| );
 | |
| ```
 | |
| 
 | |
| `MyComponent` 的 state 应该使用键值对 `{ text: "Hello" }`,进行初始化。
 | |
| 
 | |
| ```js
 | |
| assert(
 | |
|   Enzyme.mount(React.createElement(MyComponent)).state('text') === 'Hello'
 | |
| );
 | |
| ```
 | |
| 
 | |
| 单击 `button` 元素应该运行 `handleClick` 方法,并使 state `text` 为 `You clicked!`。
 | |
| 
 | |
| ```js
 | |
| async () => {
 | |
|   const waitForIt = (fn) =>
 | |
|     new Promise((resolve, reject) => setTimeout(() => resolve(fn()), 250));
 | |
|   const mockedComponent = Enzyme.mount(React.createElement(MyComponent));
 | |
|   const first = () => {
 | |
|     mockedComponent.setState({ text: 'Hello' });
 | |
|     return waitForIt(() => mockedComponent.state('text'));
 | |
|   };
 | |
|   const second = () => {
 | |
|     mockedComponent.find('button').simulate('click');
 | |
|     return waitForIt(() => mockedComponent.state('text'));
 | |
|   };
 | |
|   const firstValue = await first();
 | |
|   const secondValue = await second();
 | |
|   assert(firstValue === 'Hello' && secondValue === 'You clicked!');
 | |
| };
 | |
| ```
 | |
| 
 | |
| # --seed--
 | |
| 
 | |
| ## --after-user-code--
 | |
| 
 | |
| ```jsx
 | |
| ReactDOM.render(<MyComponent />, document.getElementById('root'))
 | |
| ```
 | |
| 
 | |
| ## --seed-contents--
 | |
| 
 | |
| ```jsx
 | |
| class MyComponent extends React.Component {
 | |
|   constructor(props) {
 | |
|     super(props);
 | |
|     this.state = {
 | |
|       text: "Hello"
 | |
|     };
 | |
|     // Change code below this line
 | |
| 
 | |
|     // Change code above this line
 | |
|   }
 | |
|   handleClick() {
 | |
|     this.setState({
 | |
|       text: "You clicked!"
 | |
|     });
 | |
|   }
 | |
|   render() {
 | |
|     return (
 | |
|       <div>
 | |
|         { /* Change code below this line */ }
 | |
|         <button>Click Me</button>
 | |
|         { /* Change code above this line */ }
 | |
|         <h1>{this.state.text}</h1>
 | |
|       </div>
 | |
|     );
 | |
|   }
 | |
| };
 | |
| ```
 | |
| 
 | |
| # --solutions--
 | |
| 
 | |
| ```jsx
 | |
| class MyComponent extends React.Component {
 | |
|   constructor(props) {
 | |
|     super(props);
 | |
|     this.state = {
 | |
|       text: "Hello"
 | |
|     };
 | |
|     this.handleClick = this.handleClick.bind(this);
 | |
|   }
 | |
|   handleClick() {
 | |
|     this.setState({
 | |
|       text: "You clicked!"
 | |
|     });
 | |
|   }
 | |
|   render() {
 | |
|     return (
 | |
|       <div>
 | |
|         <button onClick = {this.handleClick}>Click Me</button>
 | |
|         <h1>{this.state.text}</h1>
 | |
|       </div>
 | |
|     );
 | |
|   }
 | |
| };
 | |
| ```
 |