Pull to refresh

Comments 30

Почему нет пометки что это перевод, автор явно не разработчик

И как можно вот так написать было recetDefaults

ведь это не опечатка

Спасибо, что заметили очепятку в сигнатуре. Глаз замылился. Исправлю и залью новую версию.

Буду признателен за другие замечания, если увидите.

А почему Вы решили, что автор не разработчик?

"При следующей компиляции и построении вашего проекта библиотека будет скачана в ваш проект."

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

То что автор статьи и автор пакета одно лицо, я доказывать Вам не буду. Наверное, вы не дочитали статью до конца и не посмотрели репозиторий проекта.

более того оно не правильное

А что по сути неверно в этом предложении?

Каком построении блин, сборки бандлером видимо имеется ввиду, ну ладно, давно ли у нас пакет при npm install скачивается после сборки проекта, как он вообще скомплиируется тсом и соберётся если скачивается только после этого.

Ну я собственно дальше не читал уже да, зачем?

Код смотреть мне зачем? Уже не хочется, такую фигню можно самому написать а после таких фраз не охото этот пакет юзать, вдруг он у меня скачается после сборки тем более

Хорошо посмотрел немного

log(...args: any[]) {

if (this.logLevel <= 1) console.log(this.generateOutput(args));

}

console.log невозможно будет заменить на другой аутпут, он здесь захажкожен а должена инжектится сущность с определенным интерфейсом, dependency inversion принцип не используется, это не хорошо.

Не должен класс логгера знать о console.log браузера это не его зона ответственности

Более того это сайд эффект усложняющий тестирование и делающий функцию грязной

То есть если я захочу писать лог в файл например в ноде, ваша библиотека увы не подойдёт. Либо захочу писать в дом ноду в браузере

А можно было бы подкидывать например функцию с определенным интерфейсом извне и управлять потоком логов как угодно, а так же потенциально делать коробочные варианты, например как в winston

И это я увидел сразу, через секунд 10

Не нужно грубить мне в ответ, может быть я резко выражаюсь, зато по делу, это ведь лучше чем ничего? Если вас задело прошу прощения.

PS за классы респект

То есть если я захочу писать лог в файл например в ноде, ваша библиотека увы не подойдёт.

Скорее всего да. Или вы будите разбираться сами с перенаправлением в файл на уровне stdout.

Она не для этого. Она для высокофункциональных браузерных приложений, что и написано во первых строках.

А тащить в пользовательский браузер монста только ради логирования мне не хотелось. А тут - 62Кв. Это то, что надо.

Тащить ниче не надо, консоль лог это вы как раз затащили лишнего, вашей либе он не нужен она другими вещами занимается, то что та среда где вы запускаете вашу либу имеет встроенный консоль лог это не значит что это не зависимость

Ваша либа про уровни и мб форматирование а не про вывод в конкретное место, я для примера привел файл чтобы было нагляднее, аутпут может быть совершенно любым и не должен определяться самой любой, ее задача "что" а как и куда уже не ее зона

Тот же file logger не обязан быть частью данной библиотеки, он может быть в другом пакете

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

...

и обеспечивает логирование в программах, написанных на  TypeScript.

...

Она не для этого. Она для высокофункциональных браузерных приложений

Эм. На TS пишут только под браузер? а "любой новый язык" тоже только под браузеры?

Ваш комментарий я расцениваю как повод уточнить в документации к новой версии фокус, на что библиотека ориентирована и на что нет.

 а "любой новый язык" тоже только под браузеры

С чего Вы это взяли? Я пишу о том, что в любом языке программирования (на чтобы он не был нацелен) должно быть встроенное логирование.

ведь это не опечатка

Ещё раз спасибо. Уже исправлено в тексте и в библиотеке.

Интересно, чем автора не устроил log4js, стабильная известная библиотека с теми же фичами и 4 миллионами инсталлов в неделю

Авторы пакета сами пишут (цитата):

Although it's got a similar name to the Java library log4j, thinking that it will behave the same way will only bring you sorrow and confusion.

(Хотя ее название похоже на название библиотеки Java log4j, думать, что она будет вести себя так же, принесет вам лишь огорчения и замешательство.)

Тут Вы правы. Надо подчеркнуть легковесность библиотеки. То, что моя библиотека инспирирована Log4J не значит, что она повторяет её функциональность. В Log4J вбиты десятилетия труда программистов.

Дело не в этом.

Log4J, как и любой правильный логгинг, никак не влияет ни на время исполнения, ни на функциональность основного кода. Всё должно выполняться полностью асинхронно, сообщения должны кэшироваться, а главное — их порядок обязан сохраняться даже при вызовах из разных потоков/вкладок/страниц на разных устройствах. Если обработчик вывода упал, замедлился, крысы-кабель-перегрызли — это не должно сказаться на выполнении основного кода никак. И еще миллиард нюансов, многие из которых — даже Log4J решает отвратительно, или не решает никак.

Просто обернуть вывод в консоль — красивой оберткой — никакого смысла не имеет. Вот ребята из OpenTelemetry как-то пытаются двигаться в правильном направлении, хотя для JS этот путь очень тернист.

Просто обернуть вывод в консоль — красивой оберткой — никакого смысла не имеет.

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

Что я ясно вижу, о чем уже писал в другом комментарии - надо еще активнее подчеркнуть, что это библиотека для работы а браузере, а не в тяжелых серверных приложениях на Node.Js. В простых серверных предложениях - возможно.

Так сбор телеметрии на клиенте это тоже нормально. Хотя вроде как чаще решается другими библиотеками ... Но тем не менее как простой вариант может быть и снимок лога.

Почему это полезно, потому что есть редкие баги, которые редко воспроизводятся во время разработки, а потом неожиданно появляются в рантайме. И их надо повторить, и это намного быстрее, чем пытаться словить его не зная всех шагов. Либо баг, который редкий, его никто не репортит просто потому что лень, но мог быть выявлен при анализе телеметрии.

Почему это полезно,

Никто не оспаривает полезность сбора и анализа серверных логов. Это - огромная тема, большое количество открытых и платных инструментов.
Но эта библиотека предназначена совсем для другого.
Типичный Use Case в production: Пользователь сообщает о проблеме с приложением. Сотрудник отдела поддержки решает, что проблема в клиентской части (которая работает в браузере). Он просит пользователя включить логирование, открыть вкладку консолли в браузере и повторить операцию, при которой происходит ошибка, скопировать вывод из консоли и послать в поддержку.

Он просит пользователя включить логирование, открыть вкладку консолли в браузере и повторить операцию, при которой происходит ошибка, скопировать вывод из консоли и послать в поддержку.

Очень сложно. А если это мобильный браузер? Странное решение.

Почему нельзя сделать отправку логов на сервер автоматически для конкретно одной учетной записи (пользователя)?

Пользователь жалуется - ему в учетке ставят флаг "отладка". Дальше логи автоматически только с этой учетки будут накапливаться на сервере.

отправку логов на сервер автоматически

Сделать это можно. На это даже тикет в GitHub заведён. Но это не сделано, потому что я сначала делаю то, что нужно моим проектам, и если это может быть интересно и другим, предлагаю миру. А моим проектам этого пока не нужно.

Реализованный вариант лучше предложенного в следующих ситуациях, когда

  • приложение высоко-автономное и, возможно, глючит как раз при отсутствии связи с сервером,

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

  • в стране пользователя существуют строгие ограничения на передачу и хранение приватных данных (а если пользователь их сам отослал, сам за это и ответчик),

  • пользователи хотели бы иметь понятный контроль над данными, которые они отсылаю куда-либо,

  • провайдер услуги (использующий в своём коде эту библиотеку) не хочет тратиться на поддержку сервисного сервера.

In processFile. ERROR 100:

смутило что эта часть лога пишется руками. как тогда парсить тонны логов, если этот кусок пишет человек? а если в одном месте он напишет ERROR, а в другом месте случайно ЕRROR. не видите разницу? а символ E кирилл цей во втором случае :)

это к тому, что должен быть шаблон формирования текста лога в зависимости от каких-то условий - текущая дата время, контекст логгирования, уровень ошибки, само сообщение это как минимум. И из этих кубиков можно состряпать шаблон, предположим некоторый jinja синтаксис:

[{{dd.mm.yyyy hh:mm:ss}} _ {{context}}]
{{logLevel}}: {{message}}

Дата и уровень логирования и так появится в выводе. Помещать контекст Вам никто не запрещает, но библиотека это делать и не заставляет. Проблема в том, что message часто бывают неразличимы, поскольку одни и те же параметры выводятся в разных местах функции или ловится ошибка, которая может тоже в разных местах выскочить одна и та же. И вы, анализируя лог, не в состоянии понять, в каком месте кода она выскочила и залогирована.

Именно для этого я советую сознательно различать точки логирования.

Это ИИ так нарисовал. В моём промте этого не было.

Кстати, я просил только нарисовать рубку со штурвалом и столом, на котором лежит бортовой журнал, чернильница и перо. А приглядитесь - он стол со стеночками ограничительными нарисовал и чернильницу закрытую. Понимает морскую специфику 😉.

Я конечно не эксперт, но некоторые моменты меня смутили. А именно:

  • Как-то странно что в generic библиотеке логирования описаны peerDependencies ангуляра

 "peerDependencies": {
    "@angular/common": "^17.3.0",
    "@angular/core": "^17.3.0"
  },
  • Ссылка на репозиторий наверное должна вести в актуальный репозиторий, а не на конкретную ревизию

"repository": {
    "type": "git",
    "url": "https://github.com/vsirotin/communist-web-shop/blob/27a176cca19c90156de625f77d0fd47f7d874774/projects/log4ts"
  },
  • Неконсистентное форматирование кода. Посмотрите в сторону prettier.

// ━━━━━━━━━━━━━━━━━━━━━━━━━┑ Есть пробел перед ":"
constructor(private logLevel : number = 2, readonly path: string = "") { }
// ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┙Нет проблела перед ":"
  /**
  * Logs a stack debug to the console.
  * @param {any[]} args - Information parts for log message.
  */
  debug(...args: any[]) {
    if (this.logLevel <= 0) console.debug(this.generateOutput(args));
  }

// Комментарий куда-то сместился влево
  /**
* Logs a message to the console.
* @param {any[]} args - Information parts for log message.
*/
  log(...args: any[]) {
    if (this.logLevel <= 1) console.log(this.generateOutput(args));
  }
  • Потенциальный crash приложения, если вдруг будет циклический JavaScript объект. console.log в такой ситуации отработает корректно.

 if (typeof arg === 'object') {
      return JSON.stringify(arg);
 }
  • Потенциальные утечки памяти. Вы храните все логгеры в Map, но я не вижу как можно удалить один конкретный логгер. Есть только clearAllLoggers, который не факт что вызовется. Попробуйте посмотреть в сторону WeakMap.

  • Метод setLogLevelsByAllLoggers и setLogLevel делают почти одно и тоже (дублирование кода). Почему просто не сделать параметр searchPath в setLogLevel опциональным и устанавливать значения во всех логгерах если он не передан?

  • Вместо метода containsPath можно было бы обойтись регулярным выражением.

  • Зачем defaultPathPostfix в LoggerFactory public?

  • Зачем LoggerFactory это класс если имеет только static методы? Такого же эффекта можно добиться если переписать класс на функции и экспортировать только публичные.

  • Если уж так хочется в ООП, то его нужно реализовывать правильно. А как правильно, можно посмотреть тут на примере. В данный момент ощущение что LoggerFactory это недобилдер-недофабрика ещё и синглтон.

  • Множественные опечатки

    • defaultLogLeevl

    • recetDefaults

    • mathc to searchPath

    • unic name

Если Вам вдруг нужен удобный функциональный логгер для браузера, посмотрите в сторону consola. Как будто бы он удовлетворяет всем Вашим потребностям.

Большое спасибо за потраченное время и конструктивные предложения.
Я постараюсь спокойно разобраться с Вашими замечаниями и предложениями.
На это мне потребуется некоторое время.

Потенциальный crash приложения, если вдруг будет циклический JavaScript объект.

За замечания по форматированию и очепяткам ещё раз спасибо.
А как возможен crash приложения, я не понял. Не могли бы Вы переслать пример, который ломается? Как я понимаю, для этого вся библиотека вам не понадобится. Можно в личку.

Потенциальные утечки памяти

Почему? Не могли бы Вы описать это подробнее?

но я не вижу как можно удалить один конкретный логгер

Такая возможность действительно не предусмотрена. Зачем это может быть нужно? Удаление всех логгеров сразу и так сделано в целях перестраховки.

Есть только clearAllLoggers, который не факт что вызовется.

Почему?

Метод setLogLevelsByAllLoggers и setLogLevel делают почти одно

Не соглашусь. По моему опыту первый полезен в продакшине, а второй при разработке.

Вместо метода containsPath можно было бы обойтись регулярным выражением

Да, вы правы. Это рудимет от более сложной задумки. Но это внутренности и это работает.

Зачем defaultPathPostfix в LoggerFactory public?

Чтобы можно было просто его сменить.

Зачем LoggerFactory это класс если имеет только static методы? Такого же эффекта можно добиться если переписать класс на функции и экспортировать только публичные.

В каждом логируемом классе LoggerFactory вызывается только один раз.
Поэтому LoggerFactory.doSomething() для меня предпочтительнее чем LoggerFactory.getInstance().doSomething()

Если уж так хочется в ООП, то его нужно реализовывать правильно. А как правильно, можно посмотреть

Нет, в ООП я в своей жизни наигрался. А как правильно - вопрос спорный. Сначала надо договориться о критериях правильности.

Множественные опечатки

Спасибо, в следующей версии исправлю. (Возможно, уже сегодня). Очепятки - моя беда :-(

Если Вам вдруг нужен удобный функциональный логгер для браузера, посмотрите в сторону consola. Как будто бы он удовлетворяет всем Вашим потребностям.

Да нет, как будто бы совсем не удолетворяет. Возможно, в браузере он и работает, но заточен под Ноду. И самого главного - управления выводом на лету я там не увидел.

Я бы в статье такого плана добавил бы сравнение как минимум с самыми популярными уже существующими решениями. Типа популярных Winston и Pino и т.д. Мне кажется нужно подсвечивать преимущества и недостатки для общего понимания аудитории. Короче я бы раскрыл больше раздел про мотивацию.

Но вообще вы очень правильно делаете, что системно создаете продукты, которых самим не хватает. Это верный путь!

правильно делаете, что системно создаете продукты, которых самим не хватает. Это верный путь!

Спасибо. Да, путь верный. Но даже по некоторым комментария к этой статье видно, насколько различны представления о том, что надо.
И много времени тратится на шлифовку.
Но... остаётся надеяться, что кому-то это потребуется тоже.

Sign up to leave a comment.

Articles