mesodiar

Having me on those pictures are the prove that I was there

Author: mils Page 2 of 3

บันทึกฮาล์ฟมาราธอนครั้งแรก

ก่อนอื่นเลย เราเริ่มวิ่งแบบจริงๆจังๆแบบนับระยะ ก็ประมาณ 2-3 ปีที่แล้ว

ช่วงประมาณปีแรกก็วิ่งออกกำลังกายทั่วไป ซึ่งต่อมาก็รู้ว่าเป็นกีฬาเดียวที่เราถนัดมากที่สุดและชอบที่สุด

ช่วงแรกๆของปีนั้นก็แค่รักษาสุขภาพ เข้าฟิตเนสครั้งหนึ่งก็วิ่งลู่ไม่ถึง 3-4 กิโล หรือบางทีก็ไปสนามกีฬาของมหาลัย ก็ได้ระยะที่ไม่ต่างกัน

จนวันหนึ่งเปิดไอจีแล้วเห็นรูปเพื่อนถ่ายรูปคู่กับเหรียญ

นั่นเป็นครั้งแรกที่ทำให้รู้ว่าการเป็นนักกีฬาวิ่งมันไม่ได้ห่างไกลเกินเอื้อม

หลังจากนั้นไม่นานเราก็ได้ลงวิ่งในงานของ “เดิน-วิ่งการกุศล ศัลยศาสตร์รามาธิบดี” (จำได้แม่นเลย)

ตอนนั้นลงไปแค่ 5 กิโล เป็นระยะที่เรียกว่าเดิน-วิ่งเพื่อสุขภาพ’

เป็นการวิ่งจริงจังครั้งแรกบนท้องถนนในกรุงเทพ ซึ่งก็ชอบเอามากๆ

จนเมื่อวิ่งถึงเส้นชัย ก็พบว่าตัวเองยังไม่ทันเหนื่อยเลย และพอดีกับที่งานนั้นไม่แจกเหรียญสำหรับระยะ 5 โล (ตอนนั้นมีระยะให้ลง5 โลและ 10 โล)

ความอยากได้และความเหนื่อยนิดเดียวเลยบอกกับตัวเองว่า ‘เฮ้ย เราน่าจะทำได้นะ’


จนเราเริ่มลงวิ่งมินิมาราธอน หรือ 10 km

บวกกับตอนนั้นเองเราก็เริ่มวิ่งหนักขึ้นๆ จาก 3-4 กิโลมาเป็น 5-7 กิโล ซึ่งเหตุผลหลักก็ไม่ได้คิดจะซ้อมวิ่งมินิอย่างเดียว บางครั้งก็แค่วิ่งปาไป 7-8 โลเพียงเพราะอยากเอาชนะใจตัวเอง

อันที่จริงจะเรียกว่าเสพติดก็ได้ เพราะก่อนวิ่งเราจะตั้งเป้าหมายเอาไว้ว่าจะวิ่งเท่าไร เช่นวันนี้นอนพองั้นวิ่งสัก 7 โลดีกว่า หรือวันนี้เรียนหนักหน่อย งั้นวิ่ง 5 โลพอ

พอเราวิ่งครบเป้าหมายก็จะเกิดอาการฟินเล็กๆ บ่อยครั้งที่บอกกับตัวเองวันนี้เหนื่อยๆแต่ก็ยังวิ่งถึงเกณฑ์ปกติที่วิ่งได้นี่นา แล้วก็ฟินนน

สิ่งที่ฟินนอกจากวิ่งครบแล้วก็คือความรู้สึกหลังวิ่ง แน่นอนว่าหลังออกกำลังกายก็จะรู้สึกดีเป็นปกติ

และสิ่งที่ฟินที่สุดอีกอย่างหนึ่งคือการได้เห็นพระอาทิตย์ตกตอนที่วิ่งเวลาเย็นๆค่ำๆ

นั่นอาจจะเป็นเหตุผลที่พาเราวิ่ง 10 โลได้เรื่อยๆตลอดปี


เราลงวิ่งงาน 10 km มาตลอด 2 ปี

จากที่เคยวิ่งระยะนี้ใช้เวลา 1:30 ชม. ก็ขยับมาเป็น 1:20, 1:15 , 1:13 ชม. และมีงานวิ่งที่มากกว่า 10 โลนิดหน่อย

pace ค่อยๆดีขึ้น จาก 8 ไป 7 ปลายๆ พอ 7 ปลายๆก็ไป 7 ต้นๆจนถึง 6 เลย

แต่เหมือนความรู้สึกมันตันอยู่แค่นี้

เวลาวิ่งใน 10 km ที่เราตั้งใจมา จะยากมากในการเริ่มวิ่งจากจุดสตาร์ท

เราต้องวิ่งซิกแซกไปมา เพื่อที่จะวิ่งเร็วในระดับที่ถนัดของตัวเองแต่มันยากเพราะคนที่เยอะและวิ่งช้ากว่า

เราเลยเริ่มตั้งคำถามกับตัวเองว่า หรือ 10 km มันไม่พอสำหรับเราแล้ว ?

ตอนนั้นก็มีเพื่อนเราคนหนึ่งที่ชอบวิ่งมากๆ ชวนเราไปวิ่งตลอด รวมถึงชวนวิ่ง 21 km ด้วย

เราก็ได้แต่ปฏิเสธเพราะไม่คิดว่าจะไหว แต่เหมือนคำถามเมื่อกี้มาตีกลับมาถามเราใหม่

เราไม่เคยคิดจะวิ่งระยะ 21 km แต่ความรู้สึกที่อยากพิสูจน์ตัวเองเหมือนกับในหลายครั้งที่เราชอบไปงานมาราธอน และมองคนวิ่งฮาล์ฟ, ฟูลมาราธอนว่าโคตรเจ๋งว่าเขาวิ่งไปได้ยังไง

เอาวะ ลองก็ลอง

ประจวบกับมีงาน Bangkok Midnight Marathon โผล่มาในช่วงที่คิดว่าตัวเองกำลังว่างจากธุระพอดี

เลยลงฮาล์ฟมาราธอนไป และเตรียมตารางซ้อมฮาล์ฟ

ซึ่งก็ซ้อมได้เพียงครึ่งๆ ที่คิดว่าว่างจากธุระก็ไม่ได้ว่างเอาเท่าไร ติดเรียน ติดสอบ ติดเที่ยวตปท. เป็นช่วงที่ทำงานไปด้วยและเรียนไปด้วยพร้อมๆกัน

การซ้อมก็มีอันล่มไป ไม่ได้ซ้อมตามตารางที่วางไว้

จนถึงวันงานจริงๆ

เราก็เตรียมใจเอาไว้ และตั้งเป้าไว้ที่ 3 ชม.

ต้องทำได้ดิวะ

เราบอกกับตัวเองอย่างนั้นตั้งแต่รับ BIB และเสื้อ

ถึงแม้ระยะวิ่งสูงสุดที่เคยทำจะแค่ 12 โลก็ตาม


งานนี้วิ่งตอนกลางคืน เริ่มวิ่งตอนตีสาม เป็นงานวิ่งที่มาคนเดียวซึ่งก็ไม่ใช่ครั้งแรก

ตั้งแต่จุดสตาร์ท เสียงในหัวบอกต้องทำได้ดิวะชัดเจนมาตลอด

กิโลที่  1  ต้องทำได้ดิวะ

กิโลที่  2 “ต้องทำได้ดิวะ

กิโลที่ 3 “ต้องทำได้ดิวะ

กิโลที่ 4 เหมือนเสียงต้องทำได้ดิวะค่อยๆแผ่วลง

การไม่ซ้อมวิ่งมาเป็นอย่างนี้นี่เอง

เหลือวิ่งอีกตั้ง 17 โล จะวิ่งได้ยังไง


เคยมีรุ่นพี่คนนึงบอกว่า พี่เขาเจอมารผจญตอนกิโลที่ 16

เสียงมารจะลอยเข้ามาและถามว่า “เรามาที่นี่ทำไม” “เวลานี้ควรจะได้นอนไม่ใช่เหรอ” “เลิกดีกว่าน่า”

แต่นี่เรายังไม่ถึงกิโลที่ 16 เลย ในใจก็คิดว่าจะไหวไหมนะ

ตอนนั้นหิวน้ำมากๆ แวะบูธน้ำตลอดทาง ดีที่เจอบูธที่แจกกระป๋องสปอนเซอร์เลยมีแรงฮึดขึ้นมา

จนวิ่งต่อไปกิโลที่ 5, 6, 7, 8 จนถึง 9

เห้ย 9 โลแล้วเหลือระยะอีกแค่ 1 มินิมาราธอนเอง

แต่จากที่วิ่งฉลุยก็เริ่มสลับเดินมากขึ้น มากขึ้น แล้วปาไปกิโลที่ 10, 11 โดยที่เราไม่รู้ตัว

จนเห็นป้ายกิโลที่ 12

จนเลยป้ายไปก็ดีใจเล็กๆ เอาวะ  break high score แล้ว !

แต่ตอนนั้นขาและเท้าเริ่มแข็ง เริ่มเจ็บมากๆเวลาเดินแล้ว

เลยตัดสินใจที่จะวิ่งมากกว่า กลายเป็นวิ่งเหยาะๆเจ็บน้อยกว่าเดินเร็ว

กิโลที่ 13, 14, 15, 16 ก็เป็นไปด้วยความทรมานที่เพิ่มขึ้นเรื่อยๆ

จนสัมผัสได้ว่านิ้วเท้าเริ่มเจ็บ เริ่มปวดข้อเท้าทุกครั้งที่ก้าว

แต่ก็เอาวะ นี่มันอีก 5 โลเอง !

ละก็วิ่งสลับเดินไป สลับแซงคนข้างหน้าบ้าง คนข้างหลังก็สลับแซงไปบ้าง

และพบว่าวิ่งกับใกล้ๆกลุ่มคนที่วิ่งเหยาะๆเยอะๆก็จะมีแรงฮึดวิ่งมากกว่ากลุ่มที่เดินกันหมด

พอมากิโลที่ 17-18

งาน BMM นี้จ้างกองเชียร์มาเชียร์ข้างสนามด้วย

ก่อนขึ้นสะพานพระราม 8 ขาขึ้นฝั่งราชดำเนิน ก็จะมีกองเชียร์ใหญ่จุดหนึ่ง

เต็มไปด้วย เสียงกลอง เสียงคนพูดสู้ๆนะค้า” “สู้ๆค่า

เรื่องตลกอย่างหนึ่งคือพอได้ยินคำว่าสู้ๆ

เท้ามันเบาขึ้นมาทันที

อยู่ๆเท้าที่แข็งๆมันสาวก้าวได้ไวเหมือนไม่มีอะไรเกิดขึ้น

นี่มันจิตวิทยาล้วนๆเลย..


พอมาถึงบนสะพานพระราม 8 ราวๆ กิโลที่ 19-20

หยุดที่บูธน้ำสุดท้ายพร้อมหยิบแก้วน้ำดื่มและตัดสินใจวิ่งต่อ

..นั่นเป็นสิ่งที่ผิดพลาดมากๆ

บูธนั้นเป็นบูธสุดท้าย และเป็นบูธที่มีสเปรย์ป้องกันตะคริว

กิโลที่ 20 จึงเป็นไปด้วยความ(โคตร)ทรมาน

ขาและเท้าไม่ไหวอีกแล้ว

ได้แต่เดิน แม้จะวิ่งก็วิ่งอย่างเจ็บๆ

ป้ายอีก 700 m” ค่อยๆผ่านไป

ป้ายอีก 500 m” ผ่านไป

ป้ายอีก 150 m”

เส้นชัยไกลจังวะ

ในตอนแรกที่คิดว่าจะลงงานนี้

เคยคิดตลอดว่าตอนเข้าเส้นชัยจะต้องร้องไห้ มีความอีโมชันนอล มือปาดน้ำตา อีกมือรับเหรียญบอกพี่คนแจกเหรียญว่า ฮือ นี่ฮาล์ฟแรกของหนูค่ะ

จริงๆคือไม่เลย ทำใจตั้งแต่กิโลที่ 16 แล้วว่าเราต้องทำได้

และก็ทำได้จริงๆ

ส่วนหนึ่งเป็นเพราะภาพตอนที่กำลังซ้อมวิ่งในหมู่บ้านตอนซ้อมในตารางที่จัดไว้ ก็ลอยขึ้นมา

ตอนนั้นถามกับตัวเองตอนกำลังวิ่งว่าแค่นี้ก็ไม่ไหวแล้ว แล้ว  21 โลจะไหวเหรอ

ตัดภาพมาตอนนี้ กำลังรับเหรียญและเสื้อ Finisher

มันก็คงประมาณนี้มั้ง

ps. จบด้วย 3.11 ชม. (จาก runtastic 21.91 km) ซึ่งมากกว่าที่คิดไว้ 11 นาที เพราะอีกิโลที่ 20 นี่ล่ะ ตอนนั้นวิ่งตาม pacer 3 ชม.ติดๆเลยจนขาไม่ไหวละ ไปก่อนเลยค่ะพี่

และจบฮาล์ฟนี้ด้วยไม่มีเสียงมารเข้ามาเลย สุดท้ายแล้วเสียงมารก็คงเป็นเสียงสะท้อนในใจเรานี่เอง

(แต่ถ้าลงฟูลก็ไม่แน่)

[Cron] Automate Tweet บอกเวลาด้วย Python กันเถอะ

  1. สิ่งแรกที่ทำต้องผูกเบอร์เข้ากับ twitter setting ปกติของเราก่อนถึงจะสร้าง application ได้
  2. เข้า https://apps.twitter.com/ และ Create New App ขึ้นมา และกรอกเฉพาะข้อมูลที่จำเป็น
  3. ใน Application settings ตรง Access level ให้เลือกเป็น Read and write เพื่อให้เรา send tweet ได้
  4. แถบ Key and Access Token ให้กดปุ่ม generate ขึ้นมา

โดยของที่จำเป็นทั้งหมดที่ต้องใช้มี 4 ตัวคือ consumer key, consumer secret, access token
และ access token secret

Read More

[Cron] เขียน slackbot ส่ง notification เตือน standup meeting

โจทย์คือ เราต้องการสร้าง Slackbot เพื่อแจ้งเตือนใน channels ที่เรา subscribe ไว้ ตอนเวลา 9.59 น.ตอนเช้า เพื่อในเวลา 10.00 น.จะมี standup meeting ที่ Pronto Tools

Set up environment

$ virtualenv venv

$ source venv/bin/activate

โหลด slackclient API library เพื่อที่จะให้เราส่งและรับข้อความจาก Slack ให้ได้ก่อน

(venv) $ pip install slackclient

  1. ก่อนอื่น ไปสร้าง Slack team ให้เรียบร้อย หรือจะใช้ที่มีอยู่ก็ได้

2. เข้าไปสร้าง bot

note : แต่ชื่อจะซ้ำกับ Slackbot ซึ่งเป็น bot จริงๆของ Slack ไม่ได้นะ

Read More

[Cron] มาเล่น cron กันเถอะ

เคยไหมที่เราจะต้องทำ task แบบเดิมๆในช่วงเวลาเดิมๆของทุกวัน ในการพัฒนาระบบ web application

แทนที่เราจะมานั่งรันคำสั่งแบบเดิมๆทุกวัน Cron ได้ตอบโจทย์ของเรา

Cron คืออะไร

Cron มีไว้เพื่อ schedule tasks ที่เราต้องการเช่น กำหนด ณ เวลาเท่านี้ จะต้องทำ task นี้ มันก็จะไปทำ task ตาม script ที่เราเขียนเพื่อไปรัน server

หรือเรียกอีกอย่างว่าเป็น Job scheduler ซึ่งใช้สำหรับ Unix-like operating systems นั่นเอง

และแต่ละ task หรือ job จะถูกเรียกง่ายๆว่า Cron Jobs

ถ้ายังนึกภาพกันไม่ออก ยกตัวอย่างเช่น

  • บริษัท A มีระบบ membership ซึ่งมีจำนวนสมาชิกเยอะมาก เมื่อถึงวันหมดอายุของสมาชิกลูกค้า ก็ไม่จำเป็นมานั่งกด deactivate หรือลบ  account เอง
  • บริษัท B อยากส่ง newsletter email ในรอบวัน หรือประจำเดือน  เพื่อโปรโมตสินค้า
  • บริษัท C มีระบบที่เช็คว่าใน website มีอะไรพังบ้าง จึงอยากให้มีระบบแจ้งเตือนเข้า email ทันที

 

Syntax

ตัวอย่างเช่น

Read More

[Python] Django project: 03 Make it dynamic

2016-12-27-180347-801168

สิ่งที่เราต้องการคืออยากให้ข้อมูลเก็บลงใน database และนำมาแสดงบนหน้า html

 อย่างแรกที่ต้องทำ หนีไม่พ้นสร้าง Model แน่นอน

Django Model

สร้าง model ใน kitten/models.py

from __future__ import unicode_literals

from django.db import models

class Kitten_image(models.Model):

   image_name = models.CharField(max_length=100)

    width = models.CharField(max_length=10)

    height = models.CharField(max_length=10)

เมื่อเราสร้าง model ของตัวเองแล้ว สิ่งที่เราต้องทำคือ add model ไปยัง database

Read More

[Python] Django Project: 02 Get image via API

kittens

สืบเนื่องจาก โพสนี้ 

เราต้องการที่สร้างโปรแกรมใส่ width และ height ที่ต้องการเพื่อให้แสดงรูปภาพแมวเหมียวขึ้นมา

จากคราวที่แล้ว เมื่อเซตอัพเสร็จ ก็ถึงเวลาที่จะสร้างโปรแกรมจริงๆจังๆสักที

Create own application inside project

(venv)   django_project$ python manage.py startapp kitten

แต่เราต้องบอก Django ว่าสร้าง application อะไรไป

เข้าไปใน mysite/settings.py

INSTALLED_APPS = [

    ‘django.contrib.admin’,

    ‘django.contrib.auth’,

    ‘django.contrib.contenttypes’,

    ‘django.contrib.sessions’,

    ‘django.contrib.messages’,

    ‘django.contrib.staticfiles’,

    ‘kitten’,

]

——

Manage URL

การที่ Django จะรู้ว่ามีหน้าไหนบ้างนั้น เราต้องระบุใน mysite/urls.py

from django.conf.urls import include, url

from django.contrib import admin

urlpatterns = [

    url(r’^admin/’, admin.site.urls),

    url(r”, include(‘kitten.urls’)),

]

Django ตามหา url ยังไง? คำตอบคือใช้สิ่งที่เรียกว่า Regex หรือ Regular Expression ซึ่งมันคือ search pattern

ตัวสำคัญๆ เช่น

  • ^  ตอนเริ่ม text
  • $  ตอนจบ text
  • \d  สำหรับ digit
  • + to indicate that the previous item should be repeated at least once
  • () to capture part of the pattern

เราเพิ่ม  url(r”, include(‘kitten.urls’)) มาเพื่อให้เวลาเรียก url ก็จะไปตามหา url ใน application kitten ก่อน เพื่อการจัดการที่เป็นระบบที่ง่ายขึ้น

ดังนั้นเราต้องสร้าง urls ของ application ของเรา

from django.conf.urls  import url

from . import views

urlpatterns = [

    url(r’^$’, views.kitten_home, name=’kitten_home’),

]

เพื่อให้หน้า http://127.0.0.1:8000/ จะแสดงหน้า homepage ของ application

โดยเราให้ views ไปเรียก kitten_home ไปยัง url ^$

kitten/views.py

from django.shortcuts import render

import requests

def kitten_home(request):

       return render(request, ‘kitten_home.html’, {})

แต่สิ่งที่เกิดขึ้นคือ

screen-shot-2559-12-26-at-10-12-35-am

ไม่มีไฟล์ kitten_home.html นั่นเพราะเรายังไม่มี template มาให้แสดงนี่เอง

——

Create Template

เราสร้าง directory ขึ้นมาใหม่ภายใน kitten ของเราเพื่อแยกพวกไฟล์ template ต่างหาก

โดยสิ่งที่เราสร้างคือ form รับขนาด width และ  height และเมื่อกดปุ่ม Get Image จะต้องได้รูปแมวเหมียวออกมา

template/kitten_home.html

[code language=”html”]

{% load static %}

<html>
<head> <title> Kitten </title>
</head>
<!– Latest compiled and minified CSS –>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
<!– Optional theme –>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap-theme.min.css" integrity="sha384-rHyoN1iRsVXV4nD0JutlnGaslCJuC7uwjduW9SVrLvRYooPp2bWYgmgJQIXwl/Sp" crossorigin="anonymous">
<!– Latest compiled and minified JavaScript –>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js" integrity="sha384-Tc5IQib027qvyjSMfHjOMaLkfuWVxZxUPnCJA7l2mCWNIpG9mGCD8wGNIcPD7Txa" crossorigin="anonymous"></script>
<body>
<div class="row">
<div class="col-md-4"></div>
<div class="col-md-4">
<form class="form-inline" method="post">
{% csrf_token %}
<div class="form-group">
<label for="input_width">Width</label>
<input name="input_width" type="text" class="form-control" id="input_width" placeholder="insert width"></div>
<div class="form-group">
<label for="input_height">Height</label>
<input name= "input_height" type="text" class="form-control" id="input_height" placeholder="insert height"></div>
<button type="submit" class="btn btn-default" value="OK">Get Image</button>
</form>

<img src="{% static ” %}{{ kitten_image }}"></div>
<div class="col-md-4"></div>
</div>
</body>
</html>

[/code]

โดยการรับ input นั้น จะต้องตรวจสอบผ่าน forms.py ว่าต้องรับเป็น field type อะไร

kitten/forms.py

from django import forms

class KittenForm(forms.Form):

    input_width = forms.CharField(label=’input_width’, max_length=10)

    input_height = forms.CharField(label=’input_height’, max_length=10)

(https://docs.djangoproject.com/en/1.10/topics/forms/#forms-in-django)

kitten/views.py

[code language=”python”]

from django.shortcuts import render
from .forms import KittenForm
import requests
def kitten_home(request):
if request.method == ‘POST’:
form = KittenForm(request.POST)

if form.is_valid():
url = "http://placekitten.com/g/" + form.cleaned_data[‘input_width’] + "/" + form.cleaned_data[‘input_height’]
kitten = requests.get(url)
f = open("kittens.png", "w")
f.write(kitten.content)
f.close
else:
form = KittenForm()
return render(request, ‘kitten_home.html’, {‘kitten_image’: "kittens.png"})

[/code]

ครั้งแรกที่เข้า url นี้จะเป็น GET request จะเป็นการสร้าง form instance เปล่าๆ และในครั้งถัดไป เมื่อ submit ก็จะเป็นการ Post Request เข้าสู่ form instance

return render(request, ‘kitten_home.html’, {‘kitten_image’: “kittens.png”})

นั้นจะส่ง path ของรูปภาพที่เราสร้างไว้ กลับไป render ที่ template ใน ด้วยวิธี การจัดการกับ static files

ใน settings file จะมี STATICFILES_DIRS บอกถึง path ที่ให้ไปหา static files ที่ได้เก็บไว้

STATICFILES_DIRS = [
    os.path.join(BASE_DIR),
]

ทำให้เมื่อเราใส่ {% static ” %}{{ kitten_image }} เท่ากับการใส่  path ปัจจุบัน + ภาพไฟล์

ทำให้ template แสดงรูปภาพออกมาได้ตามนี้

{% load static %}
 <img src="{% static '' %}{{ kitten_image }}">

(https://docs.djangoproject.com/en/1.10/howto/static-files/)

Screen Shot 2559-12-27 at 9.13.25 AM.png

[Python] Django Project : 01 Setting up

Django คืออะไร ?

Django คือ open source web framework ตัวหนึ่งที่

1. ฟรี

2. เขียนด้วย Python

framework คืออะไร?

framework คือตัวช่วยในการสร้าง websites ที่ทำให้งานเราง่ายขึ้นและสะดวกขึ้น ตัวอย่างเข่น ระบบ authentication ( sign up, sign in, บลาๆ ), การจัดการ form บน website หรือแม้การโหลดไฟล์ก็ตาม

ทำให้ปัญหาเดิมๆที่เราต้องเผชิญเวลาสร้าง websites ใหม่ๆมีน้อยลงด้วยการใช้ของสำเร็จที่ django เขาสร้างมาเรียบร้อยแล้ว

Installation

  1. install python

install Homebrew  ลง package manager ก่อนเลย เพื่อลง Setuptools และ pip ให้เรา

$ /usr/bin/ruby -e “$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)

และลง python3

$ brew install python3

2. install virtualenv

สร้าง virtual environment สำหรับ project เรา

$ mkdir django_project

$ cd django_project

$ virtualenv venv 

(http://docs.python-guide.org/en/latest/dev/virtualenvs/)

คำสั่งนี้ virtualenv venv จะ สร้าง folder ใน current directory

และเราจะเลือกใช้ Python3 ในนี้  ด้วยคำสั่ง

virtualenv -p python3 venv

3. install Django

คราวนี้เมื่อเราได้ virtualenv สร้าง environment เรียบร้อยแล้ว เราก็มาลง Djangoกันได้เลย

แต่แน่นอน ก่อนอื่นต้องมั่นใจว่าเราได้ pip เวอร์ชั่นล่าสุดก่อน

$pip install –upgrade pip

$ pip install django

ถ้า django ถูกลงแล้ว จะต้องเห็น version

$ python -m django –version

เริ่มโปรเจคกัน

อย่าลืมว่าเราต้องรันทุกอย่างของโปรเจคนี้ใน virtualenv จึงต้อง activate กันก่อน

เข้าไปใน directory ที่แล้วต้องการแล้ว

source myvenv/bin/activate

ต่อด้วย

(venv)   django_project$  django-admin startproject mysite .

คำสั่งนี้จะ auto-generate โค้ดเพื่อสร้าง Django Project ให้แก่เรา

mysite/
    manage.py
    mysite/
        __init__.py
        settings.py
        urls.py
        wsgi.py

# ต้องใช้ . ด้วย เพื่อบอก script ว่า install django ใน current directory นะ และทำให้ไฟล์ manage.py ก็จะมาอยู่ใน directory นี้ ซึ่งเป็นตัวสำคัญที่ต่อไปจะเป็นตัว start server ให้

# django-admin.py คือสคริปต์ที่จะสร้าง directory แล้ว file ให้เรา

# settings.py คือ configuration ของ website

แก้ Configuration เรื่อง Time zone กันก่อน

# เข้า mysite/settings.py ไป set เวลา timezone เซตที่ TIME_ZONE = ‘Asia/Bangkok

# ตรง debug = True

ALLOW_HOSTED = [’127.0.0.1’]

ตัว allowed_hosts เหมือนเป็นการระบุ whitelist ของ domain ว่า site ไหนปลอดภัยแก่การ respond ซึ่งตัว Django นั้นเองเป็นคนสร้าง security ตัวนี้เพื่อป้องกันปัญหาเรื่อง Phishing attack นั่นเอง

Phishing ออกเสียงเหมือน Fishing เป็นการตกเบ็ด นั่งรอเฉยๆเพื่อให้เหยื่อเข้ามาหาเอง อย่างเช่น การที่สร้าง websites ปลอม หน้าตาดูเชื่อถือ เพื่อให้เราเชื่อแล้วกรอกข้อมูลส่วนตัว คนรอเบ็ดก็วินไปได้ข้อมูลเราไปใช้ทำมิดีมิร้ายด้าย

(https://www.djangoproject.com/weblog/2013/feb/19/security/)

เซต database 

เข้ามาใน mysite/settings.py

เราเลือกใช้ SQLite เพราะเป็น default ของ python อยู่แล้ว ไม่ต้องทำอะไรเพิ่ม แต่ถ้าอยากได้ database ที่ scalable กว่าก็เลือก PostgreSQL ไปนะแจ๊ะ

DATABASES = {

    ‘default’: {

        ‘ENGINE’: ‘django.db.backends.sqlite3’,  // ไม่ก็ ‘django.db.backends.postgresql’

        ‘NAME’: os.path.join(BASE_DIR, ‘db.sqlite3’), // ถ้าใช้ sqlite3 ตัว database จะสร้างไฟล์ลงในเครื่องของเราให้เลย

    }

}

ถ้าใช้นอกเหนือ SQLite ล่ะก็ ต้องรันคำสั่ง “CREATE DATABASE database_name;” ด้วยนะ

Migrate 

ในส่วนต้นๆของไฟล์ ที่ INSTALLED_APPS จะมีชื่อของ Django Applications ต่างๆมาเป็น default ให้อยู่ละ

พวก apps เหล่านี้จะต้องใช้ database เราจึงต้อง create database ขึ้นมาถึงจะใช้ apps เหล่านี้ได้

$ python manage.py migrate

( ต้องอยู่ที่ๆมี manage.py นะแจ๊ะ)

คำสั่งนี้จะ create และ update database ไปในตัว

Start web server

มาดูหน่อยซิว่า work ไหม

(venv)   django_project$ python manage.py runserver

เปิดเข้าไปใน http://127.0.0.1:8000/ แล้วก็จะพบกับ

screen-shot-2559-12-23-at-4-30-24-pm

happy-crying-face-meme-11

เย้

[Python] เขียน API ดึงรูปแมวเหมียวมาเซฟด้วย Requests Library !

[เขียนโค้ด] เขียน API เซฟรูปแมวเหมียวด้วย Requests Library!

เราจะมาเข้าใจการใช้ Requests ด้วยวิธีง่ายๆ ด้วยการทำเรื่องง่ายๆ อย่างเช่นตัวอย่างที่จะอธิบายต่อไปนี้ คือการดึงรูปมาเซฟ นั่นเอง

เริ่มต้นเลย! เรามีเว็บไซต์ง่ายๆ http://placekitten.com/ ที่เพียงแค่ใส่ image size ใน URL ก็สามารถได้รูปแมวเหมียวขึ้นมา

เช่น http://placekitten.com/g/300/200

kittens

นั่นคือ กว้าง 300 px, สูง 200 px

สิ่งต่อไปคือ เราจะเซฟรูปยังไงนะ?

คีย์ลัดของเราคือ Requests Library

Requests คืออะไร?

Requests คือ HTTP Library ตัวหนึ่งที่เขียนด้วยภาษา Python (for human beings เป็นมิตรกับสุขภาพจิต)  ให้เราส่ง HTTP/1.1 request ไปได้ (https://github.com/kennethreitz/requests)

ตัวอย่างการใช้ requests เช่น

>>> import requests

>>> r = requests.get(‘https://api.github.com/user’, auth=(‘user’, ‘pass’))

>>> r.status_code

200

>>> r.headers[‘content-type’]

‘application/json; charset=utf8’

>>> r.encoding

‘utf-8’

>>> r.text

u'{“type”:”User”…’

>>> r.json()

{u’private_gists’: 419, u’total_private_repos’: 77, …}

เริ่มต้นด้วยการ install package นี้เข้าเครื่อง

ด้วยคำสั่ง

$ pip install requests

หรือจะ clone มาโดยตรงจากผู้สร้างก็ได้

$ git clone git://github.com/kennethreitz/requests.git

จากนั้นเราก็เริ่มโค้ดกันได้เลย!

เริ่มต้น ทำกรอบง่ายๆด้วยการสร้าง class และแบ่งเป็นคอนเซปง่ายๆดังนี้

import requests

class Kitten():

   // 1. ทำ url ให้สมบูรณ์ : การที่เราจะดึงข้อมูลจาก placekitten ได้ เราจะต้องรู้ที่อยู่ (url) ของไฟล์ที่เราต้องการจะเซฟก่อน โดยการป้อนwidth และ height เข้าไป

   // 2. เขียน request เพื่อที่จะดึงข้อมูลนั้น

   // 3. นำข้อมูลที่ดึงมา เขียนลงไฟล์ที่เราสร้างขึ้นมาในเครื่อง (เซฟรูป)

  1. เราต้องการจะทำให้ได้รูปตามที่ความยาวและความกว้างที่เรากำหนด custom เอง ดังนั้นจึงสร้างตัวแปรรับค่า

width = raw_input(“How wide do you want image to be?”)

height = raw_input(“How tall do you want image to be?”)

ค่า url ที่ได้จึงควรจะเป็น

url = “http://placekitten.com/g/” + width + “/” + height

เท่านั้นเราก็ได้ url แล้ว!

  1. สิ่งถัดไปคือ เมื่อเราได้ที่อยู่ของข้อมูลแล้ว เราก็เขียน API เรียก request เพื่อเอาค่านั้นมา โดยวิธี requests.get()

kitten = requests.get(url)

และค่าที่เราได้จะนำไปเก็บที่ตัวแปร kitten

3. นำข้อมูลที่ดึงมาเรียบร้อยแล้วลงไฟล์ที่เราสร้าง !

f = open(“kittens.png”, “w”)  // open() เป็นฟังก์ชั่น built-in ของ python เพื่อบอกว่าต้องการจะเขียนไฟล์ png ขึ้นมาใหม่ ชื่อว่า kittens แต่แค่เปิดไว้เฉยๆ ยังไม่ได้ทำอะไร

f.write(kitten.content)  // นำข้อมูลที่เราได้ดึงมาก่อนหน้า นำมาเขียนลง kittens.png ที่เปิดคาไว้ให้แล้ว

f.close // ปิดไฟล์

สังเกตว่าข้อมูลที่ดึงมานั้น( kitten) จะใช้เฉยๆไม่ได้ เพราะเราได้ kitten เป็น object ที่เป็น dictionary

ถ้าเราลอง kitten.__dict__ ดู จะเจอ

{‘cookies’: <RequestsCookieJar[Cookie(version=0, name=’__cfduid’, value=’df2b7c0cd57b968b95249e432bca8a3b91482412416′, port=None, port_specified=False, domain=’.placekitten.com’, domain_specified=True, domain_initial_dot=True, path=’/’, path_specified=True, secure=False, expires=1513948416, discard=False, comment=None, comment_url=None, rest={‘HttpOnly’: None}, rfc2109=False)]>, ‘_content’: ‘\xff\xd8\xff\xe0\x00\x10JFIF\x00\x01\x01\x00\x00\x01\x00\x01\x00\x00\xff\xfe\x00;CREATOR: gd-jpeg v1.0 (using IJG JPEG v62), quality = 65\n\xff\xdb\x00C\x00\x0b\x08\x08\n\x08\x0…. บลาๆเยอะมาก ‘ }

ใน content นั่นเองที่เก็บข้อมูลรูปภาพอยู่ นั่นคือต้องใช้ kitten.content เขียนลงไปในไฟล์ใหม่

จบคอนเซปหลักๆ เราก็ fill in โค้ดได้เลย

import requests

class Kitten():

    def get_width_and_height(self, width, height):       /// ฟังก์ชั่น เพื่อรับค่า input ของ weight และ height

        self.width = width

        self.height = height

        return (self.width, self.height)

    def get_image(self): /// ฟังก์ชั่น เพื่อสร้างรูปภาพขึ้นมา

        url = “http://placekitten.com/g/” + self.width + “/” + self.height   

        kitten = requests.get(url)

        f = open(“kittens.png”, “w”)

        f.write(kitten.content)

        f.close

        return url

width = raw_input(“How wide do you want image to be”)             

height = raw_input(“How tall do you want image to be”)

x = Kitten()

x.get_width_and_height(width, height) /// instantiate เพื่อนำค่า width และ height เข้าฟังก์ชั่นแรก

x.get_image()

จากนั้นเมื่อเรารันไฟล์ ก็จะมีคำสั่ง How wide/tall do you want image to be ?  ให้เราป้อนขนาดรูปภาพที่ต้องการลงไป

คราวนี้ใน path เราก็มีรูปแมวเหมียวขึ้นมาแล้ว เย้

400

What I’ve learned from Pronto Tools

เป็นเวลาสักพักแล้วหลังจากที่ค้างว่าจะเขียนหลังจบการฝึกงานใน 1 เดือนให้หลัง (เรียกสั้นๆว่า เบี้ยว นี่เอง)

ขอตั้งชื่อว่า What I’ve  learned from Pronto Tools

แต่ก่อนอื่นเลย ! 

Pronto ในที่นี้ไม่ใช่ร้านยีนส์นะค้า

แต่เป็น Pronto Marketing และ Pronto Tools ซึ่งเป็นบริษัทอยู่ในเครือ Pronto Group

Pronto Marketing เป็นบริษัทที่รับทำหน้าที่ดูแลเรื่อง Online Marketing และ SEO ให้ และไม่ว่าจะเป็นเรื่อง Content Management, Graphic Design หรือ Social Media 

ที่เราไปฝึกงานนั้นคือ Pronto Tools หรือ Research & Development team ( R&D team ) ที่ทำหน้าที่ focus เรื่องพัฒนา Software ให้กับ Pronto Marketing นั่นเอง

และในอนาคต Pronto Tools ก็จะรับสร้าง Tools ให้กับ SME เจ้าอื่นอีกด้วย

เอาล่ะ งั้นเริ่มกันเลย !

1. As a Giver and Taker

ก่อนอื่น ต้องเล่าถึงครั้งแรกว่ารู้จักที่นี่ได้ยังไง เมื่อประมาณตุลาคมปีที่แล้ว ( 2015 ) ได้คำแนะนำจาก ภวิน ว่าให้ลองสมัครมา Girls Learning Python ที่ Pronto จัดดูสิ ไปเรียน Introduction to Python 

ประจวบเหมาะกับตอนนั้นเอง แอบคิดๆเริ่มเล็งๆเรื่องบริษัทที่จะฝึกงาน พอลองมางานนี้ก็ติดใจ เข้าไปถาม พี่เก๋ คนสอน Python ของเราในวันนั้น (และก็ยังเป็น Agile Coach อีกด้วย) อย่างเขินๆว่าเปิดรับเด็กฝึกงานรึยังคะ 555555 

และในปีถัดมา พี่เขาก็รับเราเข้าฝึกงาน ( ตัดบทอย่างรวดเร็ว จริงๆแล้วคือจีบที่นี้หนักมาก จีบเก่ง )

พี่มีภารกิจให้ทำค่ะ ตั้งแต่ยังไม่ฝึกงาน

นั่นคือไปงาน Girls Who Dev #2 ซึ่งก็คือ สอน Python เหมือนในครั้งที่แล้ว แต่คราวนี้จะให้เราช่วยมาเป็น TA

ตื่นเต้นนนนนนนมากกกกกกจ้าาาาาาา 

เคยทำงานอาสามาก่อนแต่ก็ไม่เคยมาแนว dev กังวลเรื่องจะตอบยังไง จะอธิบายคนอื่นยังไงดี 

แต่เราก็ค่อยๆพยายามเรียนรู้แล้วก็สามารถรับมือขึ้นได้เรื่อยๆ 

ได้รู้เลยว่า Python หัวข้อเดิมแต่ในคราวนี้ แทนที่เราจะนั่งฟังอย่างเดียวเราก็เป็นคนที่ทั้งฟังทั้งพูดโต้ตอบ 

เราต้องคิดมากกว่าเดิม ต้องกลั่นความคิดแล้วพยายามอธิบายให้คนอื่นเข้าใจ 

หรือแค่บางจุดในสิ่งที่เราเข้าใจแต่บางคนไม่เข้าใจ เราก็ อ๋อออ โอเค

เรียนรู้ว่าจะสื่อสารกับมนุษย์โลกยังไงดี

สรุปคือยังไม่ทันฝึกงานก็ได้อะไรไปคิดแล้ว

ซึ่งมันเป็นประสบการณ์ที่ดีมากๆ (เรียนรู้ง่ายดี อีเว้นท์เดียวกัน)

img_0429

2. Internship, REALLY ?

ถามตัวเองว่านี่มาฝึกงานจริงดิ

เราเข้ามาฝึกงานในตำแหน่ง Junior Software Engineer 

ในช่วง 2 อาทิตย์แรก มีพี่กาน, พี่ทราย,พี่ฝัน, พี่บอส เป็นคนสอนเรื่องเบสิคต่างๆไม่ว่า Vim, Vagrant, Python, Django, Puppet, WordPress, Git, Robot Framework, Jenkins, Tableau, Machine Learning และอีกมากมาย  รวมถึงซ้อมทำ Scrum ย่อยๆโดยมีสมาชิกเป็นแก๊งเด็กฝึกงาน 

ในทุกๆเรื่องที่สอนหรือสงสัย ไม่มีกั๊ก ไม่มีทิ้ง คอยดูแลกำกับและให้คำแนะนำตลอด

จนเราแอบนึกสงสัย นี่ต้องทำถึงขนาดนี้เลยเหรอเนี้ย

แต่พอเข้ามาใน Sprint รวมกับพี่ๆ ก็เข้าใจในสิ่งที่พี่เขาตั้งใจจะให้จริงๆ 

มันมีประสิทธิภาพ

จนเราไม่รู้สึกว่าเขามองเราแค่เป็นเด็กฝึกงานแค่เพียงฝึกงานผ่านๆแล้วจบๆไป

ถ้าอยากรู้ว่าช่วงแรกเป็นยังไง วาร์ปไปนี้เลยค่า

3. But it’s just the beginning

อันที่จริงแล้ว หลัง 2อาทิตย์นั้น การเรียนรู้ก็ต่อเนื่องและเข้มข้นเรื่อยๆ ที่เรียกได้ว่าเรียนรู้ตลอดเวลา5555 

pair คู่กับ พี่ๆหรือเพื่อนอินเทิร์นด้วยกัน ทำ TDD, ลอง ทำ WordPress กับ Puppet ครั้งแรก, เรียนรู้ microservices, นั่งลุ้น CI ว่าจะเขียวไหม, หรือไป merge branch ให้ git log ไม่สวยงามให้ทุกคนสะพรึง 

ที่นี่ให้เกียรติ(และเกลียด)กับเด็กฝึกงานมากๆค่ะ ทำจริง พังจริง ตราบเท่าที่ยังไม่พัง Production 5555555

เป็นช่วงเวลาที่หาเรื่องตื่นเต้นให้ตัวเองทุกวันค่ะ

และอีกเรื่องนึง นอกจากใน  Sprint หลักๆเองที่มี Retrospective ด้วยแล้ว

มีการ Retrospective ย่อยๆสำหรับแก๊ง interns ด้วยนะ โดย พี่กาน(หัวหน้าแก๊ง) เขาก็จะมองใน  Scope ของเราว่าเราได้อะไรบ้าง ติดปัญหาอะไรไหม มีอะไรให้พี่เขาช่วยพิเศษไหม

มันก็ทำให้เรารู้ว่า response เป็นยังไง รู้จุดอ่อนของตัวเอง ยิ่งรู้ไวก็ยิ่ง realize  ได้และแก้ไขได้เร็วขึ้น 

IMG_2155.JPG

4. Participation

นอกจาก Girls Who Dev แล้ว ก็ยังมีอีเว้นท์อื่นๆที่เข้าร่วม เช่น Agile Thailand 

IMG_2313.JPG

งานนี้จัดขึ้นเมื่อเราได้ฝึกงานไปประมาณ 1 เดือนแล้ว หรือพูดอีกอย่างว่าหลังจากเราปรับตัวเข้าสู่การทำงาน Agile มาได้สักพัก

เราก็ได้มางานนี้และรู้ว่า ‘เฮ้ย มีคนอีกมากที่สนใจ Agile ไม่น้อยเลย’ ทั้งที่ยังไม่เคยทำหรือบุคลากรที่มาจากบริษัทที่นำAgile เข้ามาปรับใช้แล้ว 

ความแปลกใจนี้ก็ทำให้เราตื่นเต้นเข้าไปอีก ได้ฟังคนอื่นๆว่าเขาได้ใช้ Agile กันยังไง เหมือนหรือต่างกับเรามากน้อยแค่ไหน ไม่ว่าจะเรื่อง TDD, Environment, Scrum หรือ Kanban ที่เขาปรับๆเอาไปใช้กัน

ก็สนุกดีนะ ได้เห็นความคิดเรื่อง Agile ในมุมมองของคนอื่น 

5. Impression

เล่าประสบการณ์ ตอนนั้นได้ pair การ์ดที่ยากระดับนึง โดยทำร่วมกับพี่และแก๊งเด็ก 

ปรากฏว่า ติดปัญหาเรื่องว่าจะแสดงผลลัพท์ยังไงดี สับสนว่าจะเขียนแบบไหนดี

พี่ออยเลยแนะนำวิธีโดยจะแบ่งออกเป็น 2 เคส คือ 

เขียนผลลัพท์ที่พอเข้าใจ เป็นเคสง่ายๆ หรือ แสดงผลเป็นอีกแบบที่สวยงามกว่าและเคสที่ยากกว่า

ลองถาม Cory ( Product Owner) ว่าเขาต้องการแบบไหน 

ถ้า Cory ต้องการแสดงผลแบบอย่างที่สอง งั้นลองแบ่งการ์ดนี้เป็นอีกการ์ดให้เขา Create ให้ เพื่อผลัดไปอยู่ Sprint หน้าได้ไหม

ซึ่งตอนนั้นจริงๆก็ทำแบบแรกไปแล้วน่ะแหล่ะ 

พอเข้าไปถามจริงๆ Cory บอกว่า “It looks great !”

happy-crying-face-meme-11

หนั่มตาหลายแปบ

งานจบ ไม่ต้องไปเสียเวลากับอีกเคสที่ Logic ยากกว่า

พอจบเย็นวันนั้น พี่ออยเข้ามาพร้อมตาเป็นประกายบอกว่า 

นี่เป็นข้อดีของ Agile ซึ่งมันเจ๋งมากที่ ถ้างานที่ต้องการมันตรงและโอเคกับคนที่เขาต้องการจริงๆ ตรงกับ requirement เราก็ไม่จำเป้นต้องวกวนหรือเสียเวลา และเจ๋งมากที่ Product Owner นั่งอยู่ในห้องเดียวกับเรา การทำงานร่วมกันก็ยิ่งง่ายและมีประสิทธิภาพ 

วันนั้นเลยกลับบ้านด้วยความปริ่ม งานเสร็จแล้วเย้

6. Internship, REALLY ?

 

ถามตัวเองอีกรอบ นั่นดิ มาฝึกงานหรือมากิน

14470736_10206818818301022_32275456_n

  #กินหนักมาก

ที่นี้ให้ความสำคัญเรื่อง Work-life balance มากๆ 

Work hard, Eat hard ก็ Party hard เช่นกัน

แม้ปาร์ตี้อยู่ก็รีบกลับมาแก้งานกระทันหัน 

2FB6AF55-FAE1-4528-B20A-FFF4FBF4DF0B.jpg

หรือ เล่นอยู่ก็กินหนักเช่นกัน

IMG_1602.JPG

7. เย้

 

สุดท้ายแล้วก็ ดีใจที่ได้ฝึกงานที่นี้ค่ะ

รู้สึกว่าเป็นช่วงเวลาตัวเองโตขึ้น ซึ่งปกติแล้วคนเราก็โตขึ้นตลอดเวลา แต่พอมาที่นี้ ความชันกราฟมันสูงเป็นพิเศษ

ได้อะไรกลับไปเยอะ ไม่ว่าเรื่อง Technical หรือแนวความคิด การใช้ชีวิต

ทั้งนี้ต้องขอบคุณทุกคนไม่ว่าพี่ๆ ที่ Pronto Tools และ Pronto Marketing, Cory Brown, KD  และเพื่อนๆ Interns ที่น่ารัก 

dscf2130dscf2126dscf2097dscf2073dscf2536

dscf2502

เย้

 

อ้อ ถ้าใครสนใจมาฝึกงานหรือทำที่นี้ ลองสมัครเล้ย 

What I did in the last month, as an intern

เวลาผ่านมา 1 เดือนเต็ม ดำเนินมาถึงครึ่งทางของการฝึกงาน 

เมื่อวาน ( 1 / 7/ 16) เป็นวันที่นัดรวมเพื่อนๆที่มหาลัย ในวันศุกร์แบบนี้ต่างคนก็ต่างเลิกฝึกงาน นัดเวลากันไว้ 6 โมง แต่กว่าจะรวมตัวกันครบก็เวลาเกือบ 2 ทุ่ม 

เมื่อเจอหน้ากันเราต่างยิงคำถามใส่กันราวกับว่า 1 เดือนที่ผ่านมา ต่างคนต่างหายไปจากกันและกัน (หรืออาจจะเป็นเราคนเดียว ที่หลุดโคจรไปแล้ว) ทุกคนต่างมีประสบการณ์จากแต่ละที่ที่นำเอามาแชร์กัน

แต่ดูเหมือนว่าเราดูเป็นส่วนน้อยที่รู้สึกว่า ทำไมเราทำอะไรไม่เหมือนเพื่อนเลยนะ

และเราก็คิดว่ามันถึงเวลาที่เราต้องเล่าว่าเราทำอะไรมา 

(ที่ไม่ใช่กินแซลมอนและเช็คอินร้านบุฟเฟ่ต์)

13578479_10206227228591649_356931642_n

1. เราไปทำ Agile

Agile คืออะไร?

Agile คือวัฒนธรรมของการทำงานในการพัฒนา Software ให้มีประสิทธิภาพ มีรูปแบบที่เป็น Iterative and incremental development และเน้นคุณสมบัติตามนี้

  • ยอมรับ การเปลี่ยนแปลง
  • Interaction ระหว่างคนในทีม (Work in Team)
  • Collaboration กับ customer
  • Rapid delivery of high-quality software

และนั่นยังไม่พอ

  2. สิ่งที่เราทำ คือ Scrum

Scrum คือ subset ของ Agile หรือ method ของ Agile

” It is a lightweight process framework for agile development, and the most widely-used one.”

คือการแบ่งงานให้ย่อยๆ เล็กที่สุดแต่ทำให้งานมีประสิทธิภาพที่สุด

ยังไง?

Screen Shot 2559-07-03 at 1.46.26 PM

เอาง่ายๆ เราเริ่มจาก Product Backlog ที่จะมี Product owner เป็นตัวแทนของลูกค้า เป็นคนที่มาบอกว่า งานนี้เราต้องการอะไรในมุมมองของ Users (User stories)

scrum-process-01 (1)

จากนั้นเราก็จะซอยงานให้เป็น Backlog ใน Sprint 

ก็อย่างที่บอก มองว่า Sprint คืองานที่แบ่งย่อยลงไป ที่จะต้องทำในเวลาเท่าไรๆ 

และช่วงเวลานั้นก็จะถูกกำหนดโดย Scrum master 

Scrum master คือ คนที่ดูแลทีม คนที่ดูแลงานในภาพรวมในไปในทิศทางเดียวกัน และคุมเรื่องการตัดสินใจต่างๆ

แต่ทุกการตัดสินใจของ Scrum Master ก็จะขึ้นกับความเห็นของคนในทีมเป็นหลัก

และที่ Pronto tools ของเราก็กำหนดช่วงเวลาของ Sprint เป็น 2 weeks

3. Task Board

และอีก 1 เรื่องที่จะไม่เล่าไม่ได้เลย คือ  Task Board

หน้าตาจะเป็นแบบนี้

13566186_10206230716078834_957438259_n

มี Column : Backlog, Doing, Ready to Test, Testing และ Done

โดยงานที่แบ่งมาก็จะอยู่ในรูปของ  Post-it  Cards เป็นงานที่เราเลือกมาอยู่ใน Sprint แล้ว 

แต่ละใบก็จะมีการให้คะแนนระดับความยาก+เยอะ จากคนในทีม

ยิ่งใบที่มีคะแนนมากๆ งานก็จะใหญ่ เราก็จะพยายามแตกออกให้เป็นหลายๆการ์ดแทน

อธิบายง่ายๆ สมมติว่าเราจะหยิบการ์ดมาทำ  1 ใบ ก็จะดึงจาก Column Backlog มาไว้ ใน Doing คนในทีมก็จะรู้ว่ามีคนกำลังทำการ์ดใบนี้อยู่

และเมื่อทำการ์ดเสร็จแล้ว จะย้ายไปแปะใน Ready to Test เพื่อให้คนที่จะเป็น Tester เป็นคนตรวจงานอีกที คราวนี้ Tester ก็จะเป็นคนย้ายการ์ดไปอยู่ Testing และ Done  ต่อไป

นอกจากนี้ยังมี Burn Down Chart ด้วย

แปลงออกมาในรูปแบบกราฟ คะแนนทั้งหมดของการ์ดรวมกัน เมื่อทำเสร็จแล้วจะค่อยๆลดลงเหลือเท่าไร เราก็จะสามารถมองได้ว่า เห้ย งานเหลืออีกเยอะไหม หรือ พอใกล้จบSprint เราควรจะรีบปั่นแล้วล่ะ

13599463_10206230868042633_1503805277_n-/////-

4. Code Kata

 ทุก 9.00-9.30 เราจะมี Code kata

Code Kata คือการฝึกฝนโค้ด ทำโจทย์นั้นทุกๆวัน ทำให้ขึ้นใจจนชิล และค่อยเพิ่มเลเวลความยากขึ้นเรื่อยๆ

พี่ Kan ผู้ที่เป็นพี่เลี้ยงเด็กอินเทิร์นทั้ง 5 คน จะจับพวกเราเป็นคู่และ kata ไปพร้อมๆกัน

(ถ้าเป็นเศษก็จับพี่ๆในทีมนี่ล่ะมาคู่ด้วย)

13578553_10206227228551648_1377050263_n

และบางครั้ง พี่เขาก็จะแกล้งเราด้วยการส่งคีย์บอร์ดเทพมาให้

เทพตรงนางหน้าตาสะอาดมาก มีความ international  

เกลี้ยงทั้งอัน ไม่เห็นสักตัวอักษร 

ฝึก Touch typing ไปในตัว 

13595426_10206227228511647_2134034646_n

จากรูปนี้ก็จะเป็น Event พิเศษ — Coding Dojo

Coding Dojo คือการโค้ดต่อหน้าเพื่อนฝูง และสลับๆกันโค้ด 

พี่เปิดจอใหญ่โบร้ม เห็นกันหมดทั้งบริษัท

5. Stand-up Meeting ( Daily Scrum)

เริ่มที่  10.00 น. 

13595887_10206227280152938_707314202_n

โดยทุกคนในทีม ไม่ว่า Scrum Master หรือ Product Owner จะยืนล้อมวงกัน เหมือนเป็นการประชุมเล็กๆทุกๆวันโดยจะบอกว่า

  1. เราทำอะไรไปบ้างเมื่อวาน
  2. วันนี้จะทำอะไร
  3. เราเจอปัญหาอะไรบ้าง 

โดยวิธีการนี้ สำหรับเราคิดว่าเป็นการทำงานที่มีประสิทธิภาพมาก เพราะทุกคนจะรับรู้ว่างานถึงไหนแล้ว หรือหากเราติดปัญหาหรือต้องการความช่วยเหลือ คนในทีมก็จะสามารถช่วยเราได้ ประคองและช่วยเหลือกัน และทำให้มีความเห็นใจแก่เพื่อนร่วมงานด้วยกันอีกด้วย

อีกอย่างเหตุผลที่ยืนคือ จะได้เมื่อย ไม่มัวแต่เม้าท์กันจนไม่ไปทำงาน

6. พูดมาตั้งนาน สรุปแล้วหล่อนไปทำอะไรมาบ้าง 

13599054_10206230997845878_882601130_n

กิน !!!

#ผิด

โอเค 2 สัปดาห์แรก เป็นช่วง super duper trainee โดยจะมีพี่กานเป็นคนสอนสิ่งที่ต้องรู้ต่างๆเป็น basic ให้

โดยจะสอนไป พร้อมทำ project ขนาดย่อมๆด้วยกันเป็นทีมเด็กฝึกงาน เป็น Sprint ที่แยกตัวออกมา เสมือนจำลองการทำงานเป็นทีมก่อนเจอของจริง

 

อันที่จริงแล้ว ใน  2 สัปดาห์นี้ มองจากภายนอกแล้วก็ดูสบายนี่ ? มีคนมาเทรนด์ให้ สิ่งที่ทำก็แค่นั่งเรียนเฉยๆ

แต่เปล่าเลย ในทุกๆวันเราพบว่าทุกสิ่งที่เราเรียนที่นี้ คือเรื่องใหม่ๆ

พบว่าสิ่งที่เราเรียนมาในมหาลัย อาจไม่ได้ช่วยอะไรเราเลย

หรือพบว่าสิ่งที่เราพยายามอ่านไปสอบตอนนั้น กลับช่วยให้เราเข้าใจอย่างน่าประหลาด

เราพบว่าเรายิ่ง รู้  ในสิ่งที่ไม่รู้  ทำให้เรารู้ว่าจริงๆแล้ว ‘เราไม่รู้อะไรเลย’

ในสิ่งที่ไม่รู้ เราย่อมมีคำถามมากมายอยู่ในใจ

ในครั้งนั้นที่เรายังใหม่กับสถานที่หรือคนในทีม เราอาจจะไม่กล้าที่จะเริ่มถาม ไม่ว่าสาเหตุเพราะเกรงใจ หรือกลัวทำให้ทีมเดินไปช้าลง

แต่สิ่งที่พี่กานสอนไว้

“ไม่มีคำถามไหนที่โง่ มีแต่โง่ที่ไม่ถาม”

เพราะสุดท้ายแล้ว ทีมก็ต้องไปด้วยกัน 

หากล้มก็ล้มด้วยกัน หากสำเร็จก็สำเร็จด้วยกัน

 

ดังนั้นสิ่งที่เราทำ คือเราต้องตามหาได้ว่า

‘สิ่งที่เราไม่รู้’ คือ ไม่รู้ ‘อะไร’

ตอบคำถามเหล่านั้น แล้วก้าวไปพร้อมๆกับทีม

จากนั้นพอจบ 2 อาทิตย์แรก ก็พาหน้ามึนๆตัวเองเข้า Sprint เดียวกับพี่ๆ ช่วยทำการ์ด+เรียนรู้ โดยใช้วิธี pair กับพี่ๆเอา

ซึ่งเรื่องราวจะเป็นยังไง อีก 1 เดือนเจอกันแจ้

credit รูปจาก Agile Samurai และ http://www.zenexmachina.com/what-we-do/applications-development/index.html

Page 2 of 3

Powered by WordPress & Theme by Anders Norén