Множественный if рефакторинг - PullRequest
0 голосов
/ 07 февраля 2019

У меня есть эта функция с двумя if, где я хочу найти пользователя в зависимости от того, какой буквенно-цифровой код я получаю.Как я могу рефакторинг этого с sanctuary-js ?

//const code = '0011223344';
const code = 'aabbc';

const isNumberCode = code => !!/^[0-9]{10}$/.exec(code);
const isLiteralCode = code => !!/^[A-Za-z]{5}$/.exec(code);

const findUser = (criteria) => {
    return new Promise(function(resolve, reject) {
      setTimeout(function() {
        resolve('user object');
      }, 300);
    });
}

async function handler(code) {
    if (isNumberCode(code)) {
       const user = await findUser({id: code});
        return user;
    }
    if (isLiteralCode(code)) {
       const user = await findUser({identifier: code});
       return user;
    }

    return 'not found';
}

async function run() {
    const user = await handler(code);

    console.log(user)
}

run();

Я не могу понять, как я должен обрабатывать три различных типа: числовой код , буквальный код и не найден код .

- ОБНОВЛЕНИЕ

Вот мое функциональное решение (я так думаю):

const Code = x => ({
  chain: f => f(x),
  fold: (e, a, f) => e(x)
});

const ErrorCode = x => ({
  fold: (e, a, f) => e(x),
  findLabel: f => ErrorCode(x)
});

const PromiseToCode = promise => ({
  fold: (e, a, f) => promise.then(x => x.fold(e, a, f))
});

const NumberCode = x => ({
  fold: (e, a, f) => a(x),
  findLabel: f => PromiseToCode(f(x, {activationCode: x}, NumberCode))
});

const LiteralCode = x => ({
  fold: (e, a, f) => f(x),
  findLabel: f => PromiseToCode(f(x, {finderCode: x}, LiteralCode))
});

const checkTypeOfCode = code => {
  if (isNumberCode(code)) {
    return NumberCode(code);
  }
  if (isLiteralCode(code)) {
    return LiteralCode(code);
  }
  return ErrorCode(code);
};

const find = async (code, criteria, type) => {
  const user = findUser();
  if (!user) {
    return ErrorCode(code);
  }
  return type(user);
};

const handler2 = (code) =>
    Code(code)
    .chain(checkTypeOfCode)
    .findLabel(find)
    .fold(
        e => 'not found',
        a => 'user object find by id',
        l => 'user object find by identifier'
    )

handler2(code).then(console.log);

Но я не знаю, хороший ли это код.Также я спрашиваю про sanctuary-js, потому что считаю, что весь этот объект не хороший способ программирования.

Ответы [ 2 ]

0 голосов
/ 07 февраля 2019

Вы можете создать enum для нескольких типов ввода и использовать оператор switch, как показано ниже.

// Enum for search-parameters
var ParameterTypes = 
{
  NUMBER :1 ,
  LITERAL:2 ,
  OTHER : 3
}

function getParameterType()
{
  //responsible to get search-parameter
  return isNumberCode(code) ? ParameterTypes.NUMBER : 
    ( isLiteralCode(code) ? ParameterTypes.LITERAL : ParameterTypes.OTHER);
}

async function handler(code) 
{
    //responsible to search user
    var user;

    switch(getParameterType())    
    {
      case ParameterTypes.NUMBER : 
          user = await findUser({id: code}); 
          //console.log('number');
          break;

      case ParameterTypes.LITERAL :           
          user = await findUser({identifier: code}); 
          //console.log('literal');
          break;

      case ParameterTypes.OTHER : 
          user = 'not found';      
          //console.log('other');    
          break;
    }   

    return user;
}
0 голосов
/ 07 февраля 2019

Поскольку вы ищете более функциональную реструктуризацию, вы можете попробовать это:

Разделите ваш код на более мелкие, более независимые секции:

  • findUser: эта функцияотвечает за предоставление либо UserObject, либо Not found.
  • Создайте функцию getCriteria, которая будет иметь всю логику относительно isNumberCode или isLiteralCode и т. д. Это вернет объект критерия или undefined.
  • handler должен нести ответственность за получение критериев и на основании ответа этого возврата findUser.Здесь можно сохранить любой код очистки, но это хаб-функция, которая вызывает различные функции и возвращает результат.У него должна быть минимальная бизнес-логика.
//const code = '0011223344';
const code = 'aabbc';

const isNumberCode = code => !!/^[0-9]{10}$/.exec(code);
const isLiteralCode = code => !!/^[A-Za-z]{5}$/.exec(code);

const findUser = (criteria) => {
  return new Promise(function(resolve, reject) {
    if (!criteria) resolve('not found')
    setTimeout(function() {
      resolve('user object');
    }, 300);
  });
}

function getCriteria(code) {
  if (isNumberCode(code)) {
    return { id: code };
  }
  if (isLiteralCode(code)) {
    return { identifier: code }
  }
}

async function handler(code) {
  const user = await findUser(getCriteria(code))
  return user;
}

async function run() {
  const user = await handler(code);

  console.log(user)
}

run();
...