Tengo dos matrices de objetos JSON.
const array_one = [ {id:'a',city:'Sydney',offer:'HAS'}, {id:'b',city:'Sydney',offer:'AHR'}, {id:'c',city:'Perth',offer:'AHR'}, ]; const array_two = [ {id:'a',html:''}, {id:'b',html:''}, {id:'c',html:''}, {id:'d',html:''}, {id:'e',html:''}, ];
Actualice array_two, agregue la nueva propiedad "isEligible" = verdadero/falso, según la condición array_one (donde ciudad = 'Sydney' y oferta = 'AHR')
const array_two = [ {id:'a',html:'', isEligible: false}, {id:'b',html:'', isEligible: true}, {id:'c',html:'', isEligible: false}, {id:'d',html:'', isEligible: false}, // default false {id:'e',html:'', isEligible: false}, ];
Intenté lo siguiente:
array_two.forEach(arrayTwoItem=> { let arrayOneItem= R.find( R.propEq('id', arrayTwoItem.id)), array_one, ); // eslint-disable-next-line no-param-reassign arrayTwoItem.isElibible= R.allPass[ R.equals( 'Sydney', arrayOneItem.city, ), R.equals( 'AMR', arrayOneItem.offer, )] });
¿Cómo evitar el error de pelusa, param reasignar? ¿Cómo resolver completamente usando ramda?
probé R.assocPath, no funcionó.
Un enfoque sería escribir una función que se parezca a (city, offer) => (array_one) => (array_two) => updated version of array_two
, una que luego puede configurar con "Sydney"
y "AHR"
. Podría verse así:
const matchId = pipe (eqProps ('id'), find) const update = (city, offer) => pipe ( (xs) => (y, m = matchId (y) (xs)) => assoc ('isEligible', Boolean (m) && m .city == city && m .offer == offer) (y), map ) const array_one = [{id: 'a', city: 'Sydney', offer: 'HAS'}, {id: 'b', city: 'Sydney', offer: 'AHR'}, {id: 'c', city: 'Perth', offer: 'AHR'}] const array_two = [{id: 'a', html: ''}, {id: 'b', html: ''}, {id: 'c', html: ''}, {id: 'd', html: ''}, {id: 'e', html: ''}] console .log (update ('Sydney', 'AHR') (array_one) (array_two))
.as-console-wrapper {max-height: 100% !important; top: 0}
<script src="//cdnjs.cloudflare.com/ajax/libs/ramda/0.28.0/ramda.min.js"></script> <script> const {pipe, eqProps, find, assoc, map} = R </script>
matchId
es un ayudante simple y podría estar en línea, pero lo encuentro más legible así. La función principal crea una función de mapeo al pasar array_one
a (xs) => (y, m = ...) => ...
, y luego pasa esa función de mapeo a map
, lista para array_two
. La función de mapeo busca un registro en array_one
que tenga un id
coincidente y luego usa assoc ('isElgible', ...)
para devolver un valor con la nueva propiedad.
Estoy seguro de que si lo intentáramos, podríamos hacer que el predicado usado para isEligible
no tuviera puntos, pero creo que esto se lee así, y no me molestaría.
Escribiría una función que toma un predicado y la matriz para actualizar:
const eligibility = (city, offer, xs) => id => any(whereEq({id, city, offer}), xs); const up = pred => map(o => ({...o, isEligible: pred(o.id)})); console.log( up(eligibility('Sydney', 'AHR', array_one))(array_two) );
<script src="https://cdnjs.cloudflare.com/ajax/libs/ramda/0.28.0/ramda.min.js"></script> <script>const {map, any, whereEq} = R;</script> <script> const array_one = [ {id:'a', city:'Sydney', offer:'HAS'} , {id:'b', city:'Sydney', offer:'AHR'} , {id:'c', city:'Perth' , offer:'AHR'}]; const array_two = [ {id:'a', html:''} , {id:'b', html:''} , {id:'c', html:''} , {id:'d', html:''} , {id:'e', html:''}]; </script>