[PHP] Praca, szybkość pisania

0

Witam

Jedno z zadań o pracę:

Stwórz skrypt, który prowadzi użytkownika przez 4 kroki:
1. Formularz: pobieranie obrazka, imienia i nazwiska, podawanie nowych rozmiarów obrazka oraz koloru ramki.
2. W drugim kroku pokazujemy zeskalowany obrazek, z odpowiednią ramką i na środku obrazka w białym okręgu imię i nazwisko wcześniej wpisane.
3. W dalszym kroku rozcinasz obrazek na dwie części (już ten z napisem i kółkiem), nad jedną podpisujesz część pierwsza, nad drugą część druga (podpisujesz je w obrazku, nie jako kod HTML). Muszą to być dwa różne obrazki.
4. W czwartym dziękujesz za sprawdzenie, prosisz o podanie e-maila. Po zatwierdzeniu wysyłasz podziękowanie na e-mail wraz z całą spakowaną paczką ze skryptem.

Oceniana jest zgodność z poleceniami, jakość, styl kodu oraz wykorzystane rozwiązania i czas, w którym praca została wykonana.
Należy również pamiętać o odpowiednim zabezpieczeniu skryptu oraz estetyce części wizualnej.

Optymalny czas to godzina zegarowa.

Dobra wymiękam, 1 godzina, nie mam szans:(
I co wszędzie jest aż tak ciężko pod względem czasowym?

0

Własnie przegrałeś - Nie wymiękaj. Zrób ile potrafisz. W takich zadaniach weryfikwana jest nie tylko wiedza ale tez:

  1. Jak radzisz sobie z problemami
  2. Jak pracujesz pod presją czasu
  3. Czy wiesz czego szukać w helpach itd.

Nie ma ludzi którzy wiedzą wszystko.

0

Da radę ;)
Powiedzmy, 5 minut max na projektowanie i myślenie w jaki sposób zakodować, a reszta to już samo pisanie, pisanie, pisanie...

0

Intrygujący jest zwrot

Optymalny czas to godzina zegarowa
Tzn. niedobrze jest zrobić szybciej?

0

oferta na stanowisko projektanta webmastera, programisty i grafika? "oraz estetyce części wizualnej" :)

a tak serio to wcale nie takie trudne i wcale nie musisz zrobić całości.
Wypadniesz najlepiej spośród innych i styka.

0

Zrobię dla własnej satysfakcji. Jakbym wiedział, że programowanie to także zawody sportowy to bym się 444 razy zastanowił przed pójściem na inf.

Nie twierdzę, że to trudne, ale mi zejdzie z tym 2 dni:D. Jeszcze ładna oprawa wizualna dochodzi, szukają człowieka orkiestry do wszystkiego.

Ciekawe czy jak użyje do wybierania koloru gotowego js to będą się ciskać, ale pisać jakiegoś 'color pickera' to nie zamierzam.

I jeszcze jedna sprawa, jak mam rozumieć ramkę wokół zdjęcia, chodzi po prostu o border w CSS? czy też ma być wygenerowana graficznie? Nie wiem jak to zinterpretować.

Pozdrawiam

0

Programowanie to obejmuje także takie zawody sportowe. Pisanie czegoś pod presją czasu i jasno określone deadline'y to norma. Przy czym często bywa tak, że na początku sam oceniasz, ile Ci to czasu zajmie.

Troszkę to bez sensu, bo planowanie to zgadywanie. Wszystkiego nigdy nie przewidzisz. Ale Project Managerowie też muszą coś mieć, jakiś punkt zaczepienia. Jeśli wyskoczy coś nieprzewidzianego i robota zajmie dłużej niż oceniałeś (przy czym nikt nie chce, żebyś na tę ocenę poświęcał cały dzień), to cię tak szybko nie wyleją ;).

Co do tego zadania, to IMO nie da się go zrobić porządnie i zmieścić się w godzinie, chyba że ktoś niedawno robił coś podobnego i pisze bardzo sprawnie. I będzie miał trochę szczęścia, tj. nie będzie miał przez całą godzinę (!) zwarć w mózgu generujących literówki i inne głupie błędy, których poprawienie jest proste, ale zajmuje trochę czasu.

Może ta godzina została tylko tam umieszczona, żeby Cię wkurzyć i żebyś czuł presję. Nie musi to wcale świadczyć dobrze o firmie. Jak masz tam ciągle programować w ekstremalnym stresie i mają Ci mówić, że dobry programista zrobi pewną rzecz w godzinę, gdy tymczasem większości (nie żółtodziobów) zajęłoby to 4 lub 8 godzin, to... niech spadają na bambus. Za samo stosowanie takich mających wywołać presję sztuczek. Nie chciałoby mi się być przez takie coś bombardowanym przez 8h dziennie. A może oni tam wszyscy są 8x szybsi niż normalny programista, więc pracują tylko godzinę dziennie? ;)

Nie wiem ile by mi zajęło czasu zrobienie tego zadania -- trzeba by to sprawdzić, a nie mam ochoty -- ale podejrzewam, że dłużej niż 1h. Hm, jak będzie okazja, to zrobię wywiad z moimi znajomymi, rakietowymi programistami, którzy piszą głównie właśnie w PHP-ie i którym szybkości nie da się odmówić. Ciekawe na ile ocenią czas wykonania tego zadania.

O firmie dobrze świadczy sam pomysł na zadanie i sposób, w jaki go opisano w treści. Zwięźle i wygląda na to, że dosyć jednoznacznie, przynajmniej w kluczowych kwestiach.

Gdy szukają człowieka-orkiestry, w dodatku ultra-szybkiego, to świadczyć to może raczej o dwóch rzeczach.

Pierwsza opcja jest taka, że są taką firmą, jak prawie wszystkie inne i po prostu piszą bzdurne wymagania. Są jedną z tych firm, co ciągle pieprzą, że jakość ma dla nich ogromne znaczenie, a tak naprawdę nie robią nic żeby ją podwyższyć.

Druga opcja jest taka, że poszukują bardzo dobrych kandydatów. Są ludzie, którzy faktycznie potrafią kodować ORAZ projektować i robią obie te rzeczy bardzo dobrze. U nas designerzy są przeważnie nieukami, ale na Zachodzie ci lepsi potrafią dobrze pociąć własne layouty, czyli napisać frontend (przynajmniej HTML i CSS, czasem też JS). Rzadziej zdarzają się programiści, którzy robią dobrze i frontend i backend (PHP/Ruby/Python...), a przy okazji całkiem dobre designy.

Takich dobrych programistów, którzy potrafią projektować, znajdziemy np. w 37signals. Piszą w języku Ruby i to DOBRZE (a także w Erlangu). To oni stworzyli słynny szkielet Ruby on Rails, a interfejsy (skuteczne i dobre!) swoich aplikacji projektują sami.

Designerów umiejących kodować swoje layouty jest na Zachodzie całkiem sporo. Np. wszyscy pracujący dla Unit Interactive. Albo Jason Santa Maria, bardzo dobry designer (nie aż tak dobry koder), projektant panelu administracyjnego WordPressa. A z Polaków to na myśl przychodzi mi riddle. Oni jednak są już znacznie gorsi jeśli chodzi o backend, choć na tyle ogarnięci, że coś tam w tym PHP naskrobią. Nie uważają się jednak za wielkich programistów backendowych.

edit: Ta ramka to chyba jednak zwykły border CSS. W punkcie 3 mówią o obrazku "już z napisem i kółkiem", a o ramce nie wspominają.

0

No dzięki za dodanie trochu otuchy.

Napisałem m.in metodę sprawdzającą upload, i tu pytanie czy jest bezpieczne, mniemam, że nie jest:)

public static function upload($field_name, $allowed_ext, $max_size = '1K', $upload_dir = 'uploads/') {
        $file = $_FILES[$field_name];
        if (isset($file['error'])
                AND isset($file['tmp_name'])
                AND $file['error'] === UPLOAD_ERR_OK
                AND is_uploaded_file($file['tmp_name'])) {

            $allowed_types = array(
                    'image/jpeg',
                    'image/png',
            );
            if (in_array($file['type'], $allowed_types)) {
                $unit = strtolower(preg_replace("/[0-9]*/", '', $max_size));
                $max_size = (int) preg_replace("/[A-Z]*/i", '', $max_size);
                switch ($unit) {
                    case 'mb':
                        $limit = $max_size * pow(1024, 2);
                        break;
                    case 'kb':
                        $limit = $max_size * 1024;
                        break;
                    default:
                        $limit = $max_size;
                }
                if ($size > $limit) {
                    self::error($field_name, 'size', array($max_size));
                } else {
                    $ext = strtolower(pathinfo($file['name'], PATHINFO_EXTENSION));
                    if (in_array($ext, $allowed_ext)) {
                        $upload_dir = $_SERVER['DOCUMENT_ROOT'].BASE_PATH.$upload_dir;
                        $img_name = uniqid().'.'.$ext;
                        $_SESSION['img_name'] = $img_name;
                        move_uploaded_file($file['tmp_name'], $upload_dir.$img_name);
                    } else {
                        self::error($field_name, 'filename');
                    }
                }
            } else {
                self::error($field_name, 'type');
            }
        } else {
            self::error($field_name, 'upload');
        }
    }

Do obrobienia grafiki zamierzam użyć gd, to dobry wybór?

I jeszcze jakie rozszerzenie polecacie do wysłania mejla z załącznikiem?

0

Skorzystaj z : http://swiftmailer.org/ i będziesz miał wysyłanie raz - dwa ;)

0

Dzięki, na pewno skorzystam.

Pozdrawiam

0

Zaznaczam, że to co zaraz zasugeruję jest trochę zależne od preferencji. Istnieją jednak obiektywne zasady mówiące o tym, że tak należy robić. W szczególności chodzi o zasadę SRP dla funkcji.

Twoja funkcja upload robi bardzo dużo rzeczy. Ja na pewno zastosowałbym refaktoryzacje "Wydzielenie metody" co najmniej raz.

Zobacz np. na ten ciąg ifów i obliczeń matematycznych zamieniający ciąg w stylu "10KB" na liczbę 10240. To się idealnie nadaje do wydzielenia i późniejszego ponownego użycia.

Nie jestem za nadmiernym lataniem po różnych klasach gdy nie jest to konieczne, ale jestem za tworzeniem minimalistycznych metod. Wydziel sobie metodę obliczającą liczbę na podstawie takiego stringu i zrób ją na początku metodą prywatną tej samej klasy -- nie musisz tworzyć osobnej klasy Utils. Dopiero gdy zechcesz użyć tej metody poza bieżącą klasą, wtedy sobie zrobisz oddzielną klasę z funkcjami pomocniczymi.

Wydzieliłbym jeszcze kilka innych metod z fragmentów kodu, które "przeszkadzają". Np. z tego pierwszego warunku w ifie zrobiłbym jedną metodę -- łatwizna, bo korzysta tylko z jednego parametru funkcji.

Zmienną $allowed_types wyciągnąłbym z tej metody i uczynił polem klasy.

A jakby wyszło, że za dużo tutaj dodaję metod i pól static, to o czymś by to świadczyło, co nie? Może trzeba zastosować wzorzec Singleton? A może samą funkcję upload trzeba wydzielić jako klasę (użyć obiektu reprezentującego metodę)?

To wszystko daję Ci pod rozwagę. Widzę tylko jedną metodę i nie znam kontekstu, w którym piszesz ten kod. Niektóre rzeczy są kwestiami preferencji i nie mam Ci zamiaru narzucać swoich. Wyglądasz jednak na wystarczająco ogarniętego programistę by samemu zrozumieć, czy te rady w tym wypadku się sprawdzą, czy nie.

0

@bswierczynski Dzięki za te sugestie.
Też widzę refaktoryzację tej funkcji. Mało tego, jestem 'wyznawcą' tzw 'composed methods' (nie wiem jak to dokładnie przetłumaczyć, w każdym razie wywodzi się to z Smalltalk'a jakby kogoś zainteresowało), czyli tak jak napisałeś tworzenia jednozadaniowych metod. Postanowiłem refaktoryzację zostawić sobie na koniec.

Też mam sentyment do tego pierwszego warunku złożonego z n-AND-ów, aż prosi się zahermetyzować to w metodzie is_valid_upload().

Sama metoda upload, jest częścią statycznej klasy do walidacji formularzy, którą stworzyłem specjalnie na potrzeby tego skryptu.

Tylko sam nie wiem czy zająć się "dopieszczaniem" tego kodu, skoro dla tego pracodawcy szybkość jest najważniejsza. Może oni programują w stylu, byle jak najszybciej, jak coś się uda wykorzystać w następnych projektach to dobrze, a jak nie to się napiszę od nowa bo i tak jesteśmy tak szybcy, że damy rady.

Siłą rzeczy, utworzenie ładnego i powtórnie wykorzystywanego kodu zajmuje trochę czasu, wtedy taki nawet skrypt to w mojej opinii to nie jest kwestia kilku tam godzin.

0

Mam ciężki orzech do zgryzienia z tym skryptem, na początek błędy, które dostaje, zresztą o wielce mówiącej treści:

Warning: imagettfbbox() [function.imagettfbbox]: any2eucjp(): something happen in D:\tools\xampp\htdocs\test\utils\image.php on line 81

Warning: imagettftext() [function.imagettftext]: any2eucjp(): something happen in D:\tools\xampp\htdocs\test\utils\image.php on line 102

Warning: imagettfbbox() [function.imagettfbbox]: any2eucjp(): something happen in D:\tools\xampp\htdocs\test\utils\image.php on line 81

Warning: imagettftext() [function.imagettftext]: any2eucjp(): something happen in D:\tools\xampp\htdocs\test\utils\image.php on line 102

Coś faktycznie 'something strange happen' w tym PHP.

Opis problemu:

Mam metodę caption, która rysuje napis na obrazku, może być to obrazek zapisany w polu instancyjnym klasy lub jakiś inny utworzony na potrzeby obróbki obrazku przechowywanego w tym polu.

Sprawa się komplikuję gdy chcę dodać napis poza obrazkiem. Tak jak jest to w punkcie trzecim tego zadania, dodać napis nad każdą połówką obrazka. Stąd też warunek if ($y < 0). Tam tworzę większy obrazek z tekstem u góry, w który włożony ma zostać obrazek główny.

Użycie tego w skrypcie wygląda tak:

$img_path = IMAGES_DIR.$_SESSION['img_name'];
$part1_path = IMAGES_DIR.uniqid().'.jpg';
$part2_path = IMAGES_DIR.uniqid().'.jpg';
Image::instance($img_path)
      ->slice(0, 50, 0, 100, $part1_path) // wartości procentowe
      ->slice(50, 100, 0, 100, $part2_path)
      ->load($part1_path)
      ->caption('Część 1', 15, 5, -50)
      ->save()
      ->load($part2_path)
      ->caption('Część 2', 15, 5, -50)
      ->save();

A sam kod tej funkcji wygląda tak:

    public function caption($caption, $font_size, $text_x = NULL, $text_y = NULL, & $image = NULL) {
        $image = isset($image) ? $image : $this->image;
        $text_color = imagecolorallocate($image, 255, 0, 0);
        $this->check($text_color, self::COLOR_ERR);
        $box = imagettfbbox($font_size, 0, $this->font, $caption);
        $text_width = $box[2] - $box[0];
        $text_height = imagefontheight($font_size);
        if ($text_x == NULL) {
            $center = ceil($this->get_width($image) / 2);
            $text_x = $center - ceil($text_width / 2);
        }
        if ($text_y == NULL) {
            $text_y = ceil($this->get_height($image) / 2) + ceil($text_height / 2);
        } else if ($text_y < 0) {
            $text_y = $text_y * (-1);
            $width = $this->get_width($image);
            $height = $this->get_height($image);
            $text_img = $this->create_blank_image($width, $height + $text_y + 10, FALSE);
            $this->check(imagecopymerge($text_img, $image, 0, $text_y,
                    0, 0, $width, $height, 100), self::MERGE_ERR);
            $image = $text_img;
            $this->check($text_img, self::DESTROY_ERR);
            $text_y = 10;
        }
        $this->check(imagettftext($image, $font_size, 0, $text_x, $text_y,
                                $text_color, $this->font, $caption), self::CAPTION_ERR);
        return $this;
    }

Wszystko się chrzani, gdy funkcja wchodzi w else_if.
Połówki zdjęć wyświetlają się, ale bez tego napisu nad nim.
Inna sprawą jest to, że pomimo użycia czcionki zawierającej polskie znaki, zamiast polskich znaków mam kwadraty.

Proszę o jakieś porady.

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