Redux жайлы қазақ тілінде бірінші мақала
- Khan
- JavaScript / 6 қаңтар 2017, 23:16
- 20582
Бұл мақала тек javascript тілін орташа деңгейде меңгерген оқырмандарға ғана арналған.
Егер React жайлы білсең, онда Redux жайлы естіген шығарсың. React-та ешқандай модель, шаблон, контроллер деп ажырататын концепт жоқ. Ол тек компонентті принцип бойынша жұмыс істейді. Бүкіл код html, css, js бір файлда сақталады, оның ішінде модель де бар. Мұндай концепттің артықшылығы Reactқа DOM-мен тез жұмыс істеуге мүмкіндік береді. Кемшілігі қиын компонент жазған кезде пайда болады. Ол кодты ары-қарай жазу тым қиын және оны түсіну де оңай емес. Дәл осы кезде сахнаға Redux шығады. Redux авторы Дэн Абрамов өзіне шабыт берген Flux және ELM екендігін жасырмай айтып, айтып тастаған.
Elm жайлы қызық факт! Бұл интерфейстер жазуға арналған тіл. Осы тілде жазылған бағдарлама, production-ға шыққанда қателерді ешқашан тұдырмайды. Ал егер ошибка шағырса, онда ол сіздің қатеңіз емес, компилятордың қателігі болып шығады екен. Себебі Elm тілінде жазылған код, javascript кодға компиляциялаған кезде, қатал тексеруден өтеді.Уау!
Императивті vs Декларативті
Redux-ке шолуды бастамас үшін, алдымен сендерге функционалды бағдарламаудың не екендігін білу қажет. Айтпадым ба әлі? Кешірім сұраймын. Elm функционалды парадигманы ұстанатын бірден бір тіл, осы бір мұрасын redux қанымен cіңірген.
Жалпы айтқанда бүкіл бағдарламалау тілдері императивті және декларативті болып бөлінеді.
Олардың айырмашылығы мына қарапайым мысалда. Егер сізге компьютерге тамақ жасату керек болса. Императивті код былай болар еді:
(statement-1) Дүкенге барып, азық-түлік аласың. (statement-2) Көкеністерді тұрап, қазан жағасың. (statement-3) Қазанға май құйасың. ... (statement-n) Тамақ піскенде мені оятасың.
дегендей тәртібі қатаң түрде белгіленген инструкциядан тұратын алгоритм сияқты.
Декларативте код болса әлде-қайда қысқа да нұсқа.
Қалай болса солай маған манты жасап бер. Компьютер ұқтың ба?
дегендей. Яғни декларативті бағдарламалауда кодтың қалай жұмыс істегені маңызды емес. Бастысы нәтежие. Декларативті бағдарламалау тілдеріне SQL, RegExp, функционалді және логикалық бағдарламалау тілдері жатады. Императивті тілдерге C++, Java, Php, Python, Ruby жатқызуға болады.
Бұл классификация жайлы толыққанды өзім де білмеймін.Сол себепті айып етпеңіздер.
Функциональді бағдарламалау. Immutablity, Pure functions
Егер қазірден бастап бастарың қатып, менің мақалам сізге физика, химия сабағына ұқсап бара жатса. Тупо зуылдатып оқып шығыңдар. Себебі бүгін болмаса ертең бастарыңа жетеді, бұл ақпарат — «бомба замедленного действия». Міне сол кезде: -Ааа! солай екен ғой. — деп айтатындарыңа сенімдімін.
Көз қорқақ, қол батыр
Elm тілінде деректер типі ешқашан өзгермейді. Javascript тілінде бұл қағида жартылай ғана дұрыс. Қарапайым типтер number, string өзгерілмейтін типтер болса, объект және массив типтері өзгеріске ұшырайды.
let str = 'testing'; str.toUpperCase(); //TESTING қайтарады str; //testing қайтарады, яғни өзгермеді let obj = {a: 'testing', b: 32}; obj.b = 10; obj; // {a: 'testing', b: 10}; қайтарады. Яғни өзгеріске ұшырайды
Бұл ерекшелікке кейін ораламыз. Ал қазір immutability — деректердің өзгермеуі екенін есте сақтасаңдар болды.
Pure function — дегеніміз өзінің аргументтерімен ғана есептеу жүргізетін функцияларды айтады. Мысалы:
// pure - таза функция function Pure(a, b) { //a және b аргументтері return a + b; } let c = 0; // impure - таза емес фунция, function Impure(a, b) { return a + c; // cебебі c левый мұнда }
Reduxтің үш басты терминдері
Ол — action, reducer және store деп аталады.
Action — қандай өзгеріс туындағанын сипаттайды. Қазақ тілде — оқиға.
Reducer — бұл pure function. Action мен ескі state-ті аргумент ретінде қабылдап, жаңа state қайтарады.Естеріңде болсын, бұл жерде маңызды акцент ЖАҢА деген сөз.Яғни immutability заңдылығына бағыну.Соңғысы ол тек өз аргументерінен алынған деректерді ғана қолдана алады(Pure function).
Store — Бұл бағдарламаңыздың моделі. Қарапайым тілмен айтқанда. Белгілі бір оқиғадан кейінгі, бүкіл бағдарламаның жағдайы немесе көрінісі, ағылшынша — state. Мысалы: меню компонентінде жаңа пункт қосылса, алынып тасталса, өзгертілсе бұл менюдың жаңа көрінісі болып есептелінеді.
Ал енді толығырақ.
Бірінші action-нан бастайық. Бұл төмендегі сигнатурасы бар қарапайым объект.
{ type: 'INCREMENT' }
Бұл жерде type міндетті түрде тұру қажет кілт(key) және оның мәні action-ның аты болып есептелінеді. Ал қалған кілттер қажеттілігене байланысты қосылу мүмкін.
Сонымен не үшін action қажет? Жауабы: ол store-ды өзгерту үшін маңызды, себебі store read-only (одан тек ақпарат алуға болады, бірақ оған тікелей жазу мүмкін емес). Дегенмен, ол store-ды өзі жалғыз өзгерте алмайды. Оған көмектесетін reducer. Ол action ның type-ына қарап, store-ды өзгертеді. Ой өтірік айтам, reducer immutability заңына бағынады ғой, яғни state-ты өзгерте алмайды, ол ескі state-ті көшіріп жаңасын қайтарады.
Мысалы:
function reducer(state=[], action) { switch(action.type) { case 'CREATEITEM': return [ ...state, // бұл spread operator, соның көмегімен ол ескі state-ті кілттерін көшіріп алады {item: 'testing'} ]; default: return state; } }
Одан кейін store жаңартылады, react store өзгергенін сезіп, қайтадан рендеринг жасайды.
Ақымақ және ақылды компоненттер(Components and Containers)
Ақымақ компонент — деген reactтің қарапайым компонентері, олар redux жайлы ештеңе білмейді. Оларға тек өздеріне келген деректерді рендеринг жасаудан басқа міндеттемелер жоқ.
Ақылды компоненттер керісінше react-redux атты қосымшамен тығыз байланысты. Оларды connect декоратор функциясы арқылы жасалынады.
const mapStateToProps = (state) => { return {// TodoList компонентке props.todos-қа binding жасайды todos: getVisibleTodos(state.todos, state.visibilityFilter) } } const mapDispatchToProps = (dispatch) => { return {// Todolist компонентке props.onTodoClick оқиғасын binding жасайды onTodoClick: (id) => { dispatch(toggleTodo(id)) // toggleTodo action-ын шақырады } } } // VisibleTodoList - ақылды компонент const VisibleTodoList = connect( mapStateToProps, mapDispatchToProps )(TodoList) // TodoList - ақымық компонент
Provider, createStore, combineReducers,
СombineReducers — бірнеше reducer-ларды біріктіреді.
cosnt reducers = combineReducers(reducer1, reducer2)
СreateStore — Бұл функция өзіне бірінші аргумент ретінде редюсерларды қабылдап, store қайтарады.
const store = createStore(reducers);
Provider — өзінен төменгі компоненттерге store-дағы ақпаратты тікелей алуға көмектеседі.
render(<Provider store={store}> <App /> </Provider>, document.getElementById('root'))
Соңына да жеттік әйтеуір. Мынау pen-де айтылған барлық код жатыр. Уақыттың аздығына байланысты, мен бұл кодты интернеттен көшіріп жазып алдым. Шыныменде маған осы мақаланы жазу үшін бірталай уақыт өтті.
See the Pen for my blog by Khangeldy (@Khangeldy) on CodePen.
-
+5
Білуімше функционалды бағдарламалау парадигмасын ұстанатын тілдер көп: haskell, scala, лисп, erlang және т.б.