Programistyczne WTF jakie Was spotkały

2

PHP 8.2 wyszło 24 listopada, czyli prawie 3 miesiące temu, a w oficjalnej dokumentacji nie ma ani słowa o dodatkowych wartościach: Np wszedł modyfikator /n: https://www.php.net/manual/en/reference.pcre.pattern.modifiers.php a dokumentacja niezaktualizowana. Czy oni są poważni w tym pehapie?

1

Czy to oglosznie jest nas serio, ponizej minimalnej: https://justjoin.it/offers/softnice-full-stack-net-developer

0

myślę, że to jakaś literówka/nieporozumienie.

  • zabrakło jednego zera? chociaż wtedy 10-15k to też mało, bo szukają kogoś doświadczonego
  • zabrakło jednego zera i informacji, że stawka jest w euro czy usd?
  • stawka jest za dzień?
  • to praca dorywcza, a nie pełen etat?
1

Makra w Rust, ale po zrozumieniu nawet ma to sens. Chyba 1 jezyk ktory robi to dobrze

0

Brat zawołał mnie, że Scratch mu się zepsuł. Okazało się, że niechcący zaznaczył opis klocka. Twórcy Scratcha nie potrafią dać tam user-select: none;?

3

Dzisiaj w bitbuckecie zobaczyłem ciekawy komentarz napisany przez leada zespołu w którym mam przyjemność (coraz mniejszą) pracować.
Poruszyłem temat jakichś zmian w kodzie i dołożył swoją odpowiedź o treści:

Długie komentarze mogą prowadzić do błędnych decyzji. Jeśli jest jakiś problem to zaznaczyć ale nie prowadzić tu dyskusji.

Czas pakować mandżur

2

Coś mi strzeliło do głowy i sobie wziąłem frontendowy task. Zrobić checkbox. Niby prosta sprawa.

Okazało się że trzeba zrobić mikrofrontend z chceckboxem...

Okeej... reszta checkboxów na stronie jest w statycznym webformem(server side rendering) i trzeba to jakoś pożenić. No to eventy przez obiekt window i się komunikujemy ze stroną na której osadzam checkbox żeby zapisać jego stan po kliknięciu przycisku save.

Okeej.. okazuje się że na stronie jest inny mikrofrontend wrzucany tam warunkowo, który zmienia zachowanie całego formularza w taki sposób że nie idzie się wpiąć pomiędzy i trzebaby go poprawić.

Okeej.. szybka pragmatyczna decyzja, chrzanić UX, będziemy zapisywać nowy stan tego checkboxa zaraz po jego zmianie, bez konieczności klikania save.

Pull Request. Każdemu kolejnemu frontasiowi muszę oddzielnie tłumaczyć skąd decyzja, każdy krzyczy że UX zły. Potem przychodzi faza akceptacji stanu rzeczy. Że tak trzeba postąpić.

Ale.. a może notyfikację dodać, a może popup. A może jakaś animację.

Dwa tygodnie implementuję chceckboxa. Bardzo chciałabym być fullstackiem ale to chyba nie dla mnie

1

Cześć,

Ostatnio zostałem dodany do kolejnego projektu, więc postanowiłem zobaczyć z czym będę miał do czynienia i znalazłem taki katalog:

.vscode/extensions.json

Co ciekawe, nie jest to przypadkowe wrzucenie, bo przed tym ta sama osoba usunęła z pliku gitignore, by nie commitować katalogu wraz zawartością vscode :D

4

Ach te tłumaczenia....... tak btw MS to lubi ;)
Zrzut ekranu 2023-03-16 o 14.24.35.png

3

@jarekr000000: a taką architekturę znasz?

The mystery was solved a few years later when we began the WorldsAway project, still consulting to Fujitsu but in a role that was much more hands-on. Our initial plan had been to work from the Fujitsu Habitat code, back porting the client to Macs and Windows, and cleaning up their server (80 users, yeesh). When we took apart their code, we finally figured out what had been puzzling us all that time: they had lost the architecture. In spite of all the information we gave them, we had completely failed to communicate how things worked. Their guys hadn’t understood the whole client-server concept, which for that day and place was somewhat exotic, so they just implemented what they knew, which was a terminal-mainframe architecture. Their “client” was basically a fancy, highly specialized graphics terminal; all the real work was done on the server. For example, when you issued a command to an object, instead of sending a command message to the object on the server, the client would send the X-Y coordinates of your mouse click. The server would then render its own copy of the scene into an internal buffer to figure out what object you had clicked on. Not only was this extremely inefficient, but the race conditions inherent a multi-user environment meant that it also sometimes just got the wrong answer. It was amazing…

http://habitatchronicles.com/2004/04/you-cant-tell-people-anything/

9

U mnie w legacy kodzie klasycznie. Generowanie id bazodanowego po stronie backendu:

  private def getNextBatchId() = run {
    bcpms_btch_refs.map(_.btch_id).max.result
  }.map(_.getOrElse(0) + 1)

Na szczęście tylko dla logów biznesowych wiec żadne dane klienta się nie tracą.
BTW nawet to działało przez prawie 4 lata bo aplikacja nie była używana z wystarczająco dużym obciążeniem. Ale ostatnio obciążenie wzrosło i getNextBatchId generuje duplikaty

UPDATE
Wersja z typem zwracanym żeby było lepiej widać że ten kod z założenia powinien działać wielowatkowo

  private def getNextBatchId: Future[Int] = run {
    bcpms_btch_refs.map(_.btch_id).max.result
  }.map(_.getOrElse(0) + 1)

run/result to są metody z Slica biblioteki do pisania typowanego SQLa.
Co do btch_id to bazodanowcny w ramach oszczędzania nazw w bazie nie zapisują prawie samogłosek, a ktoś wymyślił że encje bazodanowe mają być zgodne z tym co w bazie jest :(
Za to prefiks bcpms_ podpada pod smerfny antypattern :D

3

Umie ktoś rysować? czy sklejać memy?
taki mem mi się widzi:

Dzięki statycznemu typowaniu wiesz jaki jest typ zwracany z funkcji.
Typ zwracany z funkcji u mmnie w legacy:
Seq[(Int, Int, Seq[(Int, Int, Option[String])])]

Wyjaśnienie dla nie Scalowców - () to tuple, a [] to generyki. A Seq to sekwencja czyli ogólnie kolekcja

5

Gdy zastanawiasz się co jeszcze można skopać w Scali trafiasz na:

    for {
      _ <- someFuture.map {
        _.someMethod
      }
      result <- Future {
        someCode
      }
    } yield result 

Kod napisali seniorzy, ale fullstacki :(

Wyjaśnienie dla nie scalowców

ogólnie kod zawiera mnóstwo nadmiarowości

  1. jednoczesny for i map dla tego samego future
  2. utworzenie future dla operacja nie IO żeby zaraz dalej dostać się do wartości

A można by to ogarnąć albo jednym map

    someFuture.map { someValue =>
      someValue.someMethod
      someCode
    }

albo jednym for

    for {
      someValue <- someFuture
    } yield {
      someValue.someMethod
      someCode
    }

UPDATE jeśli kiedyś zobaczą to prawilni programiści Scali to: tak, wiem, nie powinno się używac future tylko IO, ale future to naprawde najmniejszy problem tego kodu :(

0

.NET Framework 4.7.2

IEnumerable<string> parameters = new List<string>(new[]{"1234"});
var text = string.Format("some message{0}<", parameters);

Jaką wartość przyjmie text po wykonaniu metody Format? Czy będzie to "some message1234<" tak jak założył autor? :D
Otóż odopowiedź to:

"some messageSystem.Collections.Generic.List`1[System.String]<"

Dlaczego tak jest? Zajrzyjmy do dokumentacji M$:

public static string Format(string format, object arg0)

This method uses the composite formatting feature to convert the value of an expression to its string representation and to embed that representation in a string. In performing the conversion, the method uses culture-sensitive formatting or a custom formatter. The method converts arg0 to its string representation by calling its ToString(IFormatProvider) method or, if the object's corresponding format item includes a format string, by calling its ToString(String,IFormatProvider) method. If these methods don't exist, it calls the object's parameterless ToString method.

Nawet komentarz wskazuje co ta metoda robi : "Replaces one or more format items in a string with the string representation of a specified object."

No cóż, kolejny bug do backlogu.

3

Jak ktoś mi powie że "front jest tak samo poważną technologią jak inne" to go wyśmieję.

Dostaję taki stack trace, i bądź tu mądry żeby wykminić gdzie jest błąd. Oczywiście żaden z plików wymienionych w stacktrace'ie nie jest zmieniony.

Na pewno to jest jakiś błachy błąd, przez nie uwagę; ale to że stack trace nie pokazuje dokładnego miejsca gdzie jest ten błąd moim zdaniem to kpina.

screenshot-20230609185907.png

6

Kategoria mokowanie danych na Frontendzie:
Ostatnio prawie zamockowaną wersję wydaliśmy na produkcję. Frontend zamopował prawdziwymi danymi. Potem te dane zostały dodane do bazy danych, ale frontend ich nie czytał, ale wszystko było w porządku bo to te same dane. A potem lekko się zmieniły w bazie i było zdziwienie czemu czasem działa a czasem nie XD

1

Kolega poprosił mnie o napisanie skryptu wykonującego poniższe:

  • parsowanie danych z wystawionego JSONa (3 typy informacji)
  • wyświetlenie tego na UI jako podgląd (kod HTML)

Więc zrobiłem:

  • do każdego typu informacji po 3 funkcje (parsowanie, generowanie UI, robienie czegoś jeszcze)
  • na wypadek problemów z pobraniem danych (fetch -> JSON pod URLem) wydzieliłem mu funkcję, którą sam miał sobie uzupełnić (dodać jakiś komunikat dla usera, że URL nie działa, zadzwoń do admina czy coś)

Generalnie wyszło fajnie, funkcje są niezależne i można je rozbudowywać bez ryzyka, że całość się posypie. Więc później patrzę jak to wdrożył u siebie:

  • dodał w kilku miejscach pętle for
  • zrobił dużą funkcję, która zawierała ciała 3 mniejszych funkcji, całość pod switch/case (czyli pod każdym case siedzi około 10 linijek kodu)
  • usunął kod obsługi błędu, czyi brak funkcji displayError()
  • ta duża funkcja liczy ponad 60 linijek z czego połowa łamie zasadę DRY (aż się prosi by wydzielić)
  • część mojego kodu zakomentował
4

W dużym skrócie firma klienta zajmowała się web scapingiem różnych stron z artykułami naukowymi, prawnymi itp. Idea była taka, że użytkownik loguje się na platformie i potem podaje dane dostępowe do serwisu X, my pod spodem wykorzystujemy jego login i hasło, żeby dobrać się do danych w serwisie X, a następnie całość ładnie prezentujemy w naszym serwisie. Głupie? Nie do końca, bo to jest integracja kilku źródeł danych i np. prawnicy potrzebują mieć dostęp zarówno do przepisów, jak i np. prasy branżowej bez konieczności przeskakiwania pomiędzy stronami. Bardziej ogólnym problemem jest brak API w różnych portalach. Pomyślcie o tym, jak o czymś w rodzaju wielkiej czytelni, gdzie macie dostęp i do kodeksów i do gazet i do opracowań.

WTF 1 - nie używamy API

Na moje pytanie, dlaczego nie używać API w serwisach, w których takowe jest, odpowiedź brzmiała – bo nie. Trzeba by było płacić i biznes się nie spina.

WTF 2 - loginy i hasła użytkowników

Trzymane plain textem, bo potem jakoś to selenium musi wstawić do formularza. Kto by tam się przejmował drobnostkami typu szyfrowanie. Na moją sugestię, by to przynajmniej szyfrować, padła odpowiedź „jesteśmy w chmurze i nikt tego nie ukradnie”.

WTF 3 - dostawcy

Każdy portal, do którego się logowaliśmy miał inaczej rozwiązane logowanie i pod spodem działał w inny sposób. Były apki w Reactie, były w Angularze, było też renderowanie HTMLa co każde żądanie. I tu właśnie historia @rafal95p przypomniała mi trzeci wtf, tego projektu. Każdy portal był obsługiwany osobną metodą. Taką jebitnie wielką metodą, która ogarniała logowanie i różne „ciekawe zachowania” tego konkretnego źródła danych. Metodę wybierał jebitny IF, który starał się dopasować odpowiednią metodę na podstawie URLa, który wywoływaliśmy.
Zasugerowałem, żeby to podzielić na moduły i każdy osobno wdrażać, testować itp. Stwierdzono, że nie, bo obecnie jest OK i łatwo to wszystko utrzymać. 6 tygodniu później wyleciałem z projektu. Po kolejnych dwóch tygodniach okazało się, że „łatwość utrzymania” powoduje, że nie da się dodać nowego źródła, bo jest za dużo konfliktów w kodzie i nikt nie wie, jak to ogarnąć. Trzeba było pociąć na moduły…

WTF 4 - scraping

Odbywał się z użyciem Selenium i WebDriverów, co bardzo obciążało maszyny. Zasugerowałem użycie HTTPClient przynajmniej tam, gdzie nie ma SPA pod spodem. O dziwo przeszło i było jedno wielkie wow, że można ograniczyć liczbę używanych maszyn o połowę. Potem jednak ktoś odkręcił cały temat, bo „nie możemy przepchnąć wszystkich ciasteczek”. Czytaj, trzeba napisać mapper, który zamieni ciasteczka selenium, na ciasteczka HTTPClient.

2

To chyba bug w Riderze. Fajniej się go używa jak się przywykło do IDE od JetBrains, ale nadal jest mega zbugowany.

screenshot-20230718181954.png

10

Pewnie zastanawialiście się jak rozwiązano system losowego przydziału spraw sędziom, który ma zapewniać bezstronność wydziału sprawiedliwości? Ten dokument wiele wyjaśnia i mam nadzieję będzie dla Was przykładem jak wdrożyć wymagania biznesowe w praktyce.

image

0

W c# Exception nie ma konstruktora (Exception)? ;| Jest tylko (string message,Exception)? O co kaman.

6

Strona Capgemini, tu się BE z FE w ramach kontraktu założyli kto bardziej uprzykrzy życie kandydatowi. Nie dość że trzeba wybrać 10 opcji żeby pokazały się oferty dla Krakowa, to trzeba scrollować w bok a po każdym kliknięciu wybierajka się chowa zamiast umożliwić jakiś multiselect xD

screenshot-20230727103750.pngscreenshot-20230727104114.png

4
    case 
      when lvl=8 then lvl_8
      when lvl=7 then lvl_7
      when lvl=6 then lvl_6
      when lvl=5 then lvl_5
      when lvl=4 then lvl_4
      when lvl=3 then lvl_3
      when lvl=2 then lvl_2
      when lvl=1 then lvl_1
    end 

A wy jaką dziś zbrodnię w legacy popełniliście?

6

screenshot-20230728011619.png

2

W Wirtualnej Polsce pracują bardzo dobrzy programiści. Uparli się, żeby utrudnić ludziom korzystanie z AdBlocka. To, co chcieli (chyba) osiągnąć:

  • gdy Adblock jest włączony: komunikat że trzeba wyłączyć i blokada strony
  • gdy Adblock jest wyłączony, pokazanie strony + reklam

Niestety chyba coś nie pykło bo w praktyce jest tak:

  • gdy Adblock jest wyłączony - komunikat o konieczności wyłączenia AdBlocka i blokada strony
  • gdy Adblock jest włączony - czysta strona bez reklam

Mi to pasuje, ale dobrych tam mają speców.

1

Myślicie że to na powaznie czy jakiś dziwny żart?

July 17, 2023

Dear FizzBuzzEnterpriseEdition Repository Maintainer,

Subject: Cease and Desist – Copyright Infringement

I write to you on behalf of Oracle Corporation ("Oracle"), an American multinational computer technology corporation headquartered in Redwood Shores, California.

It has recently come to our attention that the code in your repository, FizzBuzzEnterpriseEdition, on the platform GitHub, contains code which infringes upon the proprietary software of Oracle Corporation. Our concern revolves around specific sections of the repository which use Oracle's copyrighted code without permission.

The unauthorized and improper use of our copyrighted software not only infringes our rights under the United States Copyright Act (17 U.S.C. § 101 et seq.) but also violates the terms of the GNU General Public License under which Oracle's code is licensed. Such unauthorized use can expose users, developers, as well as owners to serious legal risks including but not limited to both civil and criminal penalties.

Oracle respects and encourages the collaborative nature of open-source projects, but it is critical that the rights associated with our intellectual property are maintained and enforced.

Thus, we formally demand that you immediately cease and desist all use of Oracle's copyrighted code within the FizzBuzzEnterpriseEdition repository, and certify in writing that such use has ended. We further demand that all instances of Oracle's copyrighted code be removed from the repository, from your systems and from any other places where it might reside.

We expect you to respect our rights in this matter and take prompt action to rectify this situation. Failure to comply with this cease and desist order could result in legal proceedings. Oracle reserves all rights and remedies available to it, including seeking monetary damages, injunctive relief, and an order that you pay court costs and attorney’s fees.

This letter does not constitute an exhaustive statement of Oracle’s rights, remedies, claims or defenses, all of which are expressly reserved.

We hope it will not be necessary to resort to legal action and that you will immediately cease the use of Oracle’s copyrighted materials.

Please provide written confirmation of your compliance with this cease and desist order within 10 business days from the receipt of this letter.

Yours sincerely,

Maximillian Coderight
Senior Vice President of Litigation
Oracle Corporation

cc: Legal Department
Oracle Corporation

https://github.com/EnterpriseQualityCoding/FizzBuzzEnterpriseEdition/issues/652

2

Typy "nullable" w c# są bardzo dziwne, np w funkcji

void Function(string? value) {}

value może być nullem, albo stringiem.

Ale jak widzę, nawet jak nie ma string?:

void Function(string value) {}

To nadal funkcja może być string, albo może być null :|

Różnica jest taka że jeśli mamy typ deklarację argumentu string?, to musimy się do niego odnieść value?. albo value!., no bardzo fajnie. Ale czemu deklaracja (string value) też może dostać null? :| Mega słaby design.

1
Riddle napisał(a):

Różnica jest taka że jeśli mamy typ string?, to musimy się do niego odnieść value?. albo value!., no bardzo fajnie. Ale czemu deklaracja (string value) też może dostać null? :| Mega słaby design.

Nie może, musisz we właściwościach projektu ustawić

<Nullable>enable</Nullable>

wszystkie nowe projekty mają to ustawione domyślnie, w starych projektach musisz samemu przestawić. Wyłączone ustawienie zostało dla kompatybilności wstecznej.
No i jest to tylko warning, dlatego żeby nadal można było używać starych bibliotek które nie mają określonego nullability. We własnym projekcie możesz / powinieneś ustawić WarningsAsErrors żeby przestało się kompilować:

<WarningsAsErrors>Nullable</WarningsAsErrors>

a dobrą praktyką jest traktowanie wszystkich warningów jako errorów, zazwyczaj warningi są ważniejsze niż się wydaje i powodują wiele runtime errorów

0
obscurity napisał(a):
Riddle napisał(a):

Różnica jest taka że jeśli mamy typ string?, to musimy się do niego odnieść value?. albo value!., no bardzo fajnie. Ale czemu deklaracja (string value) też może dostać null? :| Mega słaby design.

Nie może, musisz we właściwościach projektu ustawić

<Nullable>enable</Nullable>

wszystkie nowe projekty mają to ustawione domyślnie, w starych projektach musisz samemu przestawić. Wyłączone ustawienie zostało dla kompatybilności wstecznej.
No i jest to tylko warning, dlatego żeby nadal można było używać starych bibliotek które nie mają określonego nullability. We własnym projekcie możesz / powinieneś ustawić WarningsAsErrors żeby przestało się kompilować:

<WarningsAsErrors>CS8600;CS8602;CS8603;CS8625</WarningsAsErrors>

a dobrą praktyką jest traktowanie wszystkich warningów jako errorów, zazwyczaj warningi są ważniejsze niż się wydaje i powodują wiele runtime errorów

No, jak mówiłem są arugmenty ku temu. Ale to, że masz syngatury (string? value) oraz (string value) , i one obie mogą dostać nulla, pod względem design'u języka, to jest po prostu mega bieda.

Moim zdaniem, powinno być tak, że jeśli włączasz <Nullable> to deklaracja (string value) przestaje akceptować null, i powoduje to błąd kompilacji. To byłby dobry design. Zepsułoby to backwards-compatibility, co wyjaśnia czemu zdecydowano się na gorszy design - czyli że (string value) nadal akceptuje null (tylko że pokazuje warning).

1 użytkowników online, w tym zalogowanych: 0, gości: 1