• Импорт переменных React?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    1. У вас не "React просто не видит переменную $", а выпадает исключение ESLint.

    2. Модули следует экспортировать и импортировать в явном виде:

    param.js
    export default selector => document.querySelector(selector);


    Nav_btn.js
    import React, { Component } from 'react';
    import $ from './param';
    
    import './style.css';
    
    
    // ...


    3. Подобные подходы в React разработке не используют. Советую изучить возможности библиотеки и решать подобные задачи средствами React.

    Простой пример:
    const Example = () => {
      const [isActive, setIsActive] = useState(false);
      const handleClick = () => {
        setIsActive(!isActive);
      };
    
      return (
        <div>
          <div className={isActive ? 'active' : ''}>Example</div>
          <button onClick={handleClick}>Toggle active</button>
        </div>
      );
    };
    Ответ написан
  • Как подключить yandex map в react компоненту?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Можно использовать специальный компонент.
    <Script src={src} onLoad={onLoad} />

    Пример реализации
    import React from 'react';
    
    class Script extends React.Component {
    
      static displayName = 'Script';
    
      static scriptObservers = {};
    
      static loadedScripts = {};
    
      static erroredScripts = {};
    
      static idCount = 0;
    
      scriptLoaderId = `id${this.constructor['idCount']++}`;
    
      componentDidMount() {
        const { onError, onLoad, src } = this.props;
    
        if (this.constructor.loadedScripts[src]) {
          if (onLoad) onLoad();
          return;
        }
    
        if (this.constructor.erroredScripts[src]) {
          if (onError) onError();
          return;
        }
    
        if (this.constructor.scriptObservers[src]) {
          this.constructor.scriptObservers[src][this.scriptLoaderId] = this.props;
          return;
        }
    
        this.constructor.scriptObservers[src] = { [this.scriptLoaderId]: this.props };
    
        this.createScript();
      }
    
      createScript() {
        const { onCreate, src, attributes } = this.props;
        const script = document.createElement('script');
    
        if (onCreate) {
          onCreate();
        }
    
        if (attributes) {
          Object.keys(attributes).forEach(prop => script.setAttribute(prop, attributes[prop]));
        }
    
        script.src = src;
    
        if (!script.hasAttribute('async')) {
          script.async = true;
        }
    
        const callObserverFuncAndRemoveObserver = (shouldRemoveObserver) => {
          const observers = this.constructor.scriptObservers[src];
          Object.keys(observers).forEach((key) => {
            if (shouldRemoveObserver(observers[key])) {
              delete observers[this.scriptLoaderId];
            }
          });
        };
    
        script.onload = () => {
          this.constructor.loadedScripts[src] = true;
          callObserverFuncAndRemoveObserver((observer) => {
            if (observer.onLoad) observer.onLoad();
            return true;
          });
        };
    
        script.onerror = () => {
          this.constructor.erroredScripts[src] = true;
          callObserverFuncAndRemoveObserver((observer) => {
            if (observer.onError) observer.onError();
            return true;
          });
        };
    
        document.body.appendChild(script);
      }
    
      componentWillUnmount() {
        const { src } = this.props;
        const observers = this.constructor.scriptObservers[src];
    
        if (observers) {
          delete observers[this.scriptLoaderId];
        }
      }
    
      render() {
        return null;
      }
    }
    
    export default Script;
    Ответ написан
  • Как отследить изменение state?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Лучше вообще не хранить результирующие поля, а считать значения по факту.
    Ответ написан
  • Как сделать правильно Route для id и new?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    <Switch>
      <Route exact path={`${match.url}/`} component={List} />
      <Route exact path={`${match.url}/new`} component={New} />
      <Route exact path={`${match.url}/:id`} component={View} />
    </Switch>
    Ответ написан
    3 комментария
  • Как правильнее получить данные с нескольких endpoint-ов?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Данные пользователя, по-хорошему, запрашивать в экшене инициализации приложения, а загрузку товаров инициировать в cdm страницы товаров.
    Ответ написан
    Комментировать
  • Авторизация react router приватными роутами?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Приватные роуты будут гораздо удобней когда маршрутов в вашем приложении будет больше двух.
    Ответ написан
    Комментировать
  • Как вывести в компонент другие компоненты, переданные как prop?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Вы передаете в рендер функцию компонента вместо того чтобы его отрисовывать.
    Проблему исправит:
    const { header: Header, footer: Footer } = this.props;
    
    return (
      <Fragment>
        <Header />
        <Footer />
      </Fragment>
    );


    Но советую вам спроектировать этот участок иначе. Со стороны не видно никакого смысла в передаче Header и Footer в виде свойств. Их лучше импортировать в файле компонента Layout.
    Ответ написан
    Комментировать
  • Как подменить обработчик событий при наследовании в React?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Просто передавайте данные и обработчик в компонент в виде свойств:
    <DropDown onClickHandler={yourHandler} data={yourData} />

    class Dropdown extends React.component {  
      render() {
        const { data, onClickHandler } = this.props;
    
        return (
          <ul>
            {data.map((number, i) => 
              <li key={i} onClick={onClickHandler}>{number}</li>
            )}
          </ul>
        )}
    }
    Ответ написан
  • Как обновлять данных в React приложении без пересборки?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    1. Написать скрипт для деплоя приложения. json оставить в сборке. Деплоить изменения одной командой в консоли.
    2. Обновлять данные скриптом через ssh соединение. json вынести.
    3. Написать простенькую админку и обновлять данные через нее. json вынести.
    Ответ написан
    1 комментарий
  • Как переделать компонент Search в semantic-ui-react на Redux?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Вам надо в колбеке onSearchChange менять состояние фильтра. А хранить фильтр можно хоть в состоянии компонента. Пример:
    handleSearchChange = (e, { value }) => {
      this.setState({ filter: value });
    };

    Массив results, в вашем случае, будет содержать полученные из хранилища и обработанные фильтром данные.
    const results = data.filter(item => item.title.toLowerCase().includes(filter.toLowerCase()));
    Ответ написан
    4 комментария
  • Почему не работает анимация?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Анимация детей TransitionGroup срабатывает только для элементов добавленных или удаленных после монтирования TransitionGroup.

    TransitionGroup is a state machine for managing the mounting and unmounting of components over time.


    Посмотрите пример из официальной документации.
    Ответ написан
  • Какая разница между подключения реакт через консоль и по ссылке?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Ваш вопрос к самому React прямого отношения не имеет. Вопрос скорей о типах модулей и способах их использования. По ссылке вы подключаете UMD модуль, и React будет доступен как глобальный объект React или window.React. Работать с таким модулем можно хоть из тега script в html файле:
    <script crossorigin src="https://unpkg.com/react@16/umd/react.production.min.js"></script>
    <script>
      function Greetings(props) {
        return React.createElement('div', null, 'Hello, World!');
      }
    </script>

    Когда же вы устанавливаете React как npm пакет. В папку node_modules устанавливается 5 версий модуля React:
    2 версии CommonJS модулей: production и development и 3 версии UMD: production, development и prоfiling.
    Сам пакет по-умолчанию экспортирует CommonJS модуль. Версия экспортируется в зависимости от переменной окружения process.env.NODE_ENV:
    'use strict';
    
    if (process.env.NODE_ENV === 'production') {
      module.exports = require('./cjs/react.production.min.js');
    } else {
      module.exports = require('./cjs/react.development.js');
    }

    Вы используете именно CommonJS модуль, когда пишите в коде импорт из корня пакета:
    import React from 'react';
    Как правило, современной frontend разработке используется модульная система ES6, экспериментальный синтаксис и такой код требует трансляции в кроссбраузерный код и сборки. Стандартом на этом поприще сейчас являются babel и webpack.

    Советую почитать эту статью от Yandex об эволюции модульных систем JavaScript.
    Ответ написан
    2 комментария
  • Почему скрипты в React выполняются сразу?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    При загрузке приложения, скрипты из "what" выполняются сразу, чего быть не должно.

    Вы сами вызываете tt во время отрисовки компонента Home:
    <Button className="def_btn" size="xl" level="2" onClick={tt("dsdd")}>

    правильно так:
    <Button className="def_btn" size="xl" level="2" onClick={() => tt("dsdd")}>

    еще лучше написать хандлер обертку и передавать в кнопку его:
    handler = () => {
      tt("dsdd");
    };

    <Button className="def_btn" size="xl" level="2" onClick={this.handler}>


    По-хорошему, вообще не использовать jQuery в React разработке.
    Ответ написан
    3 комментария
  • Как убрать предупреждение prop type в React?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Свойством description надо передавать строку, а вы передаете объект.
    Пример правильного использования компонента:
    <Alert title="Title string" description="Description string" showIcon />;
    Ответ написан
  • Почему for(;;); вешает процесс?

    rockon404
    @rockon404
    Frontend Developer
    Условие.
    Выражение, выполняющееся на каждой интерации цикла. Если выражение истинно, цикл выполняется. Условие не является обязательным. Если его нет, условие всегда считается истиной. Если выражение ложно, выполнение переходит к первому выражению, следующему за for.

    MDN: for
    Ответ написан
    Комментировать
  • React context API vs mobX?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    MobX - библиотека для управления состоянием приложения.
    React Context API - интерфейс для передачи данных вниз по древу компонентов.

    Какие преимущества у mobX, в сравнении с React context API

    Преимуществ нет, так как у инструментов разные задачи.
    Ответ написан
  • Как правильно организовать стили для дизайн-системы?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    Надо в первую очередь в отталкиваться от задач.
    Если в вашем проекте несколько размеров кнопок для одного разрешения, несколько стилей, то необходимо передавать соответствующие свойства:
    <Button size="sm" type="outline" color="danger" />

    Если кнопка при любом значении size должна адаптироваться под разные разрешения, то имеет смысл использовать медиазапросы.

    На примере styled-components:
    const StyledButton = styled.button`
      height: ${props => props.height.sm}px;
    
      ${media.md`
        height: ${props => props.height.md}px;
      `}
    
      ${media.lg`
        height: ${props => props.height.lg}px;
      `}
    `;
    
    const getHeightProp = size => {
      switch(size) {
        case 'sm':
          return { ... };
        case 'md':
          return {
            sm: 32,
            md: 48,
            lg: 64,
          };
        case 'lg':
          return { ... };
      }
    };
    
    const Button = ({ size }) => {
      return <StyledButton height={getHeightProp(size)} />;
    }

    При использовании других инструментов используют селекторы, модификаторы, объекты стилей и тп.
    Ответ написан
    5 комментариев
  • Почему моё SPA по REST делает слишком много http-запросов?

    rockon404
    @rockon404
    Frontend Developer
    Для REST можно с запросом отдавать все связанные с сущностью или коллекцией сущностей данные:
    GET /api/posts/
    {
      posts: [ ... ],
      linked: {
        users: { ... }.
        comments: { ... },
        tags: { ... },
      }
    }

    На стороне сервера, можно складывать данные в window:
    <script>
      window.__INITIAL_STATE__ = { ... };
    </script>
    Ответ написан
    Комментировать
  • Как вывести список топ пользователей GitHub по конкретному городу, используя ReactJS и Redux?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    getUsers = () => {
      const { dispatch } = this.props;
    
      fetch(`https://api.github.com/search/users?q=Donetsk`)
        .then(res => res.json())
        .then(res => {
          return Promise.all(
            res.items.map(user => fetch(`https://api.github.com/users/${user.login}`).then(res => res.json()))
          ).then(users =>  {
            dispatch({ type: 'GET_USERS', users });
          });
        });          
    };
    Ответ написан
    Комментировать
  • Как передать ref родительскому компоненту?

    rockon404
    @rockon404 Куратор тега React
    Frontend Developer
    import React, { Component } from 'react';
    import Child from './Child';
    
    class Parent extends Component {
      childRef = React.createRef();
    
      render() {
        return (
          <Child innerRef={this.childRef} />
        );
      }
    }


    import React, { Component } from 'react';
    
    export default class Child extends Component {
      render() {
        const { innerRef } = this.props;
    
        return (
          <div ref={innerRef}></div>
        );
      }
    }
    Ответ написан
    1 комментарий