<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
    <channel>
        <title>نوشته های farshadjahanmanesh</title>
        <link>https://virgool.io/feed/@farshadjahanmanesh</link>
        <description>Senior iOS Engineer @Backbase. i love Swift and Javascript. Professional FIFA(PS5) player</description>
        <language>fa</language>
        <pubDate>2026-06-16 15:03:45</pubDate>
        <image>
            <url>https://files.virgool.io/upload/users/24631/avatar/3xelHP.png?height=120&amp;width=120</url>
            <title>farshadjahanmanesh</title>
            <link>https://virgool.io/@farshadjahanmanesh</link>
        </image>

                    <item>
                <title>از Type Safety فرار میکنیم؟</title>
                <link>https://virgool.io/@farshadjahanmanesh/%D8%A7%D8%B2-type-safety-%D9%81%D8%B1%D8%A7%D8%B1-%D9%85%DB%8C%DA%A9%D9%86%DB%8C%D9%85-erfwgird05c8</link>
                <description>Type Safetyتا الان پروژه های بزرگی رو دیدم و روشون کار کردم که توی ایران چندین میلیون کاربر دارن، آوردن اسمشون ممکن نیست ولی از من قبول کنین که واقعا اینطور بوده، یکی از بزرگترین مشکلاتی که با اون مواجه بودم، عدم رعایت Type Safety بوده. من خودمم از این قضیه جدا نبودم و خیلی وقتا این اشتباهو میکردم تا زمانیکه مقاله فرزاد (تیم لیدمون توی شرکت تپسی) رو خوندم و خودمو ملزم به رعایت این ویژگی کردم که باعث شد حس بهتری نسبت به خودم داشته باشم.وقتی به عنوان یه برنامه نویس تازه شروع به کارمون میکنیم، به این چیزا توجهی نمیکنیم و فقط سعی میکنیم برنامه دقیقا کاری که ما مد نظرمون هست رو انجام بده و اینکه چطوری این کارو انجام میده زیاد توجهی بش نمیشه. این مشکل زمانی بزرگتر میشه که یه نفر به خودش اینقدر اعتماد پیدا میکنه که میاد و توی یه شرکت به هر نحوی که شده کاری رو میگیره و استخدام میشه. برای مثال یه شرکت تازه میخواد یه اپلیکیشن iOS رو به سیستمش اضافه کنه و معمولا اولین کار چیه؟ با هزینه کمتر اپلیکیشنمون رو پیاده سازی کنیم. پس به یکی از برنامه نویس های قدیمیشون که به نظر خودشون کارش خوبه اینو میگن و اونم برای اینکه یه کار جدید و یه زبان جدید رو یاد بگیره، سرشو بالا میگیره و میگه چرا یه نفر استخدام کنین؟ بیمه، حقوق، عیدی، دردسر و ... خودم براتون این پروژه رو مینویسم و با توجه به دانش قبلی که داره به سرعت شروع به کار میکنه. یه کتاب در اون رابطه میگیره و میخونه و برنامه نویسی اون اپلیکیشن رو شروع میکنه. هر دردسری که داره یه مسئله ای که باش مواجه میشه رو به سرعت توی StackOverflow جستجو میکنه و در نهایت یه اپلیکیشن که داره کار میکنه رو میاره بالا و مدیر هم خیلی خوشحال میشه که به به افرین، چه بی دردسر و چه خوب.این میشه که یکی از بزرگترین اپلیکیشن های موجود در بازار که کاربرانش (به اجبار) برای استفاده از خدمات اون سرویس دهنده دارن ازش استفاده میکنن، بدترین، فجیح ترین و بی ارزشترین کدی هستش که تو عمرم باش کار کردم. شاید اگر این همه کاربر نداشت، اینقدر ناراحت نبودم ولی الان واقعا وقتی بش فکر میکنم که این همه اعتبار و پول بابت چیزی که واقعا ارزش کدش به اندازه ۱ میلیون تومن هم نیستش هزینه شده، قلبم درد میگیره.یکی از مشکلاتی که همه برنامه نویس های تازه کار تا متوسط ( یا حرفه ای هایی که تازه با زبان جدیدی مثل سویفت یا کاتلین یا زبان های کامپایلری) اشنا شدن باش مواجه هستند اینه که با مفهوم  Type Safety غریبگی میکنند. بذارین مثالی بزنم از این مشکل:// example 1
func setImage(imageName: String) {
    img_logo.image = UIImage(named: imageName)
}

// example 2
let username: String = Result[&amp;quotdata&amp;quot][&amp;quotusername&amp;quot]خیلی وقتا با همچین کدهایی مواجه شدیم ولی چه مشکلی با این کد ها هستش؟ در نگاه اول هیچی ولی در نگاه افراد با تجربه، این کدها ما رو به سمت مشکلات نا خواسته میبرند. چه طور؟ مثلا در مثال اول، اگر اسم فایل اشتباهی به این تابع ارسال بشه، هیچ عکس پیدا نمیشه ولی ایا این مشکل از تابع ما هستش؟ یعنی شما وقتی میخواید ایراد این کد رو پیدا کنین، دو مورد رو باید چک کنین، ایا این تابع اصلا کار کرده؟ دوم اینکه ایا عکسه پیدا شده یا نه؟ خب چرا این کارو بکنیم؟ چرا Type Safe نباشیم؟ چرا تابعمون بجای اینکه اسم عکس رو بگیره، خوده عکس رو نگیره؟ مثلا اینجوریfunc setImage(image: UIImage) { img_logo.image = image }اینجوری وقتی مشکلی باشه مطمئنیم که فقط از همونجایی هستش که داره عکس رو درست میکنه و مطمئنیم که تابع ما درست کار میکنه. حالا برای مثال دوم چی؟ باز هم همین ایراد وجود داره، کدهایی مثل بالا سر تا سر برنامه پخش میشن و میشه تصور کرد وقتی یه جایی مشکل پیش میاد ما چقدر باید بگردیم تا ایراد رو پیدا کنیم. اگر یه API اسم فیلدهاش عوض شه چقدر باید تلاش کنیم تا همه جا ایراد های مربوط به اون فیلد ها رو پیدا کنیم و تصحیح کنیمخب حالا میرسیم به این سوال که چرا باید Type Safe باشیم و Type Safety اصلا چیه؟اگر بخوام به صورت خلاصه بگم، Type Safety یعنی کمک گرفتن از کامپایلر برای جلوگیری از بوجود اومد خطاها، هرجا که میتونیم. سخت بود؟ معنی این حرفم اینه که تا میتونیم اجازه بدیم کامپایلر بدونه چی از چه نوعی هستش و چطور میتونه اونو مدیریت کنه، از کامپایلر استفاده کنیم برای به وجود اوردن خطا ها. جالبه؟ چرا باید خطا داشته باشیم؟ به این دلیل که هرچی بتونیم خطاها رو در زمان کامپایل داشته باشیم برنامه پایدار تر و استیبلتری در زمان اجرا داریم. حالا این خطا به وجود اوردن یعنی چی؟ یعنی نذاریم کسی Type اشتباه بمون بده و همون موقع بش خطا بدیم ( کامپایلر بش خطا بده) و بگیم که این تایپ چیزی نیست که ما انتظارشو داریم. برای مثال// wrong
let intergerNumber: Int = Int(apiData[&amp;quotnumberOfRows&amp;quot])!

// correct 
struct APIData: Codable {
    let numberOfRows: Int
}
let intergerNumber: Int = apiData.numberOfRowsفرق کد های بالا خیلی مشخصه و مطمئنم هممون از روش اول استفاده کردیم. ولی چرا روش دوم مطمئن تر هستش (Type Safe)؟ وقتی این مورد توی کل اپلیکیشن پخش میشه، ما با داده هایی سرو کار پیدا میکنیم که از مقدار درونشون مطمئن نیستیم و اگه برنامه نویس خوبی باشیم باید همیشه چک کنیم ایا داده مورد نظر امن هستش یا نه؟‌(یا مثه برنامه نویس های بد، همونجوری استفاده کنیم و به امید خدا، اطمینان از دادهای ارسالی رو بذاریم به عهده بقیه) مثلا تو مثال بالا اگر ما ۱۰ جا از numberOfRows  استفاده کرده باشیم و سرور اشتباها به جای عدد ۱۰، عدد ۱۰.۰۰ رو ارسال کنه، برنامه ما با خطا مواجه میشه، چرا؟ چون ما بجای اینکه چک کنیم که داده ای که داریم میگیریم  Int باشه، String میگیریم مستقیما اونو به زور به تبدیل Int تبدیل میکنیم. حالا فرض کنین این توی صفحه اول برناممون هستش، ما اینو فیکس میکنیم و میریم میبینیم بعد ۱ هفته دوباره همین ارور به وجود اومده ولی ایندفعه توی صفحات درونی (چون تا الان کسی سراغشون نرفته بود و حالا که رفته، با خطا مواجه شده)روش دوم توی مثال قبل به ما کمک میکنه تا همه برنامه از یک Type استفاده کنند و همچنین کسایی که میخوان با این ابجکت کار کنن دقیقا میدونن چی باید بدن و چی ازش بخوان و کامپایلر کمک میکنه که اگر دیتای صحیحی به این ابجکت نرسه، اخطار بده و اپلیکیشن اصلا همون موقع کامپایل تایم با خطا روبه رو میشه.پس بیاین و برای همیشه از هر Type دقیقا برای خودش استفاده کنیم و از استفاده String بجای Int یا Any بجای String و ... به شدت پرهیز کنیم تا هم کامپایلر از ما راضی باشه و هم خودمون از خودمونحالا که میدونیم  Type Safety چی هستش، میتوینم یه قدم جلوتر بریم. (این بخش چیزیه که فرزاد بش اشاره کرده و منم خیلی باش موافق هستم.)استفاده از Type با معنی ترتا حالا شده از String به جای ID استفاده کنین؟ مطمئنم شده، تا حالا شده از String بجای نام و نام خانوادگی، شماره تلفن و ادرس استفاده کنین؟ مطمئنم شده. به جمله قبل من توجه کردین؟ از String بجای نام----نام خانوادگی------تلفن------موبایل------آدرس-----آدرس عکس------آدرس وب سایت------- .... استفاده کردیم ولی ایا String تمام چیزی که ما باید بدونیم رو به ما داره میگه؟ یعنی کسی با دیدن این String دقیقا میدونه که باید چیکار کنه مثلاstruct User {
    let ID: String
    let name: String
    let family: String
    let tel: String
    let mobile: String
    let address: String
    let website: String
}توجه به این مورد چیزی هستش که ما رو یه قدم جلو تر میبره. با خودمون فکر کردیم که شاید باید Type های با معنی تری می داشتیم؟ مثلا کی گفته تلفن یه String خالیه؟ اگر بخوایم برای این تلفن Validation بذاریم، باید چیکار کنیم؟ فرض کنیم که ما از فیلد Tel توی چندتا ابجکت دیگه هم داریم استفاده میکنیم، باید برای همشون یکی یکی Validation بنویسیم و کپی پیست کنیم؟ اصلا وقتی به بقیه میگیم تلفن یه String هستش یعنی اینکه تو هرچی میخوای میتونی به من بدی مثلا &quot;dsfsfsfsfsdfsd&quot; این هم یه رشته هستش که میشه درون همه اون فیلدهای ابجکت بالا قرار داد ولی چرا این مشکل به وجود میاد؟ ما میتونیم پا رو یه قدم فرارتر بذاریم. میتونیم یه قدم Type Safe تر بشیم و میتونیم یه قدم حرفه ای تر رفتار کنیم. مثلا برای همین تلفن میتونیم اینجوری عمل کنیم:struct Phone {
    let localCode: String
    let number: String
}

struct Address {
    let city: String
    let province: String
    let address: String
}

struct User {
    ....
    let phone: Phone
    let address: Address
    ....
}این رفتار به ما کمک میکنه تا اطلاعات بیشتری درباره هر Type داشته باشیم و همچنین یه Type مشترک سر تا سر اپلیکیشنمون داشته باشیم . تمام Validation ها رو یه جا بنویسیم و تمام تغییرات رو از یه جا اعمال کنیم.وقتی میخوایم احساس خوبی نسبت به خودمون پیدا کنیم، وقتی میخوایم از یه برنامه نویس تازه کار به یه برنامه نویس با تجربه تبدیل شیم و وقتی میخوایم کدمون بهتر رفتار کنه، میتونیم قدم های صحیحی به سمت جلو برداریم که  میتونه تاپیک های زیادی رو شامل شه که قطعا یکی از اون ها اهمیت دادن به Type Safety و رعایت این موارد هستش. پس سعی کنیم از اینجا به بعد مدل هامونو درست تعریف کنیم و دقیق تر استفاده کنیم.  </description>
                <category>farshadjahanmanesh</category>
                <author>farshadjahanmanesh</author>
                <pubDate>Tue, 01 Oct 2019 17:57:43 +0330</pubDate>
            </item>
                    <item>
                <title>از Pull(Merge)-Request تا Knowledge Sharing</title>
                <link>https://virgool.io/@farshadjahanmanesh/%D8%A7%D8%B2-pullmerge-request-%D8%AA%D8%A7-knowledge-sharing-auxv2cngsjsx</link>
                <description> Merge Hellداستان از جایی شروع میشه که تیم تصمیم میگیره از گیت فلو پیروی کنه، Gitflow روشی برای مدیریت گیتمون هستش به طوریکه روند مشخصی داشته باشه و تیم همگی با هم هماهنگ باشن و یک ساختار یکپارچه رو برای کامیت ها، برنچ ها و ... داشته باشند. اگر دربارش میخواین بیشتر بدونین، میتونین از اینجا  بخونین و بدونین که برای پروژه همراه اول گیتمون رو چطور مدیریت میکردیم.خب ما توی گیت فلو از Pull(Merge) Request استفاده میکنیم که در ادامه فقط PR صداش میکنیم. PR یعنی ما یه برنچ محافظت شده داریم که قراره یه سری کد که تازه دولوپ شده یا تغییراتی روی اون انجام شده رو روش مرج کنیم و به اون اضافه کنیم. حالا بذارین با یه مثال بریم جلوما یک فیچر لاگین داریم که قراره دولوپ شه. برنامه نویس میاد و از برنچDevelop (برنچی که استیبل ترین کدمون روش هست، یعنی کدهایی که تست شده و آماده هست برسه دست مردم) یه برنچ جدید به نام Feature/Login میسازه، و شروع میکنه به کار کردن وقتی که این فیچر تمام شد، باید کارشو بیاره روی Develop که آماده ریلیز بشه. حالا اینجا دوتا سناریو هستش :خودش مستقیم مرج کنه با Develop در این حالت همه برنامه نویسا به Develop و مرج کردن روی اون دسترسی کامل دارن به همین دلیل هرگونه خطایی روش محتمل هستش و در نتیجه نمیشه گفت که Develop یه برنچ اماده ریلیز هستش.یک PR بده تا افرادی که دسترسی مرج Develop رو دارن اینکارو انجام بدندر این حالت فقط بعضی اعضا حق مرج کردن برنچ جدید با Develop رو دارن که این یه لایه محافظتی قرار میده.ما قرار رویکرد دوم رو دونبال کنیم، بعد از اینکه PR ثبت شد، یکی (یا چندتا) از اعضای دیگه تیم وظیفه داره کد جدید رو بررسی کنه به چند دلیل :‌مطمئن بشیم که قواعد و نامگذاری ها و قانونای درون تیمیمون رعایت شدنکد دقیقا کاری که باید بکنه رو انجام میدهشاید جایی بتونیم از کدهای جدیدتری استفاده کنیمشاید بتونیم اون کدو از نظر پرفورمنس بهبود بدیمشاید چیزی فراموش شده و فرد جدید که به کد نگاه میکنه متوجه اون بشهاز نظر خوانایی و قابل درک بودن کد خوبه یا نه؟شاید یه سری لاگ و ... توی کد باشه بتونیم حذفشون کنیم تست ها نوشته شدن؟مموری لیک نداریم؟کد جدید از نظر ساختار درسته؟ نمیتونیم ماژولارش کنیم تا بعدا هم ازش استفاده کنیم؟این بررسی ها به دلیل ضعف برنامه نویس اول نیست، بلکه وقتی کسی چندین ساعت زمان برای پیاده سازی یه فیچر میذاره، خیلی وقتا خسته میشه و شاید یجاهایی رو از روی خستگی یه طوری دیگه پیاده سازی کنه که با قوانین یا قواعد کل تیم متناقض باشه، یا اینکه اصلا دیدگاه های نفر دوم شاید بتونه به بهبود کد کمک کنه، اصلا شاید برنامه نویس دوم، به دلیل اینکه بخش دیگه ای از اون کد رو قبلا پیاده سازی کرده،یه چیزایی قبلا زده بود که میتونست توی کد جدید استفاده بشه و نیاز به پیاده سازی بعضی چیزا نبود و ...، همینجور که میبینیم ممکنه این عمل به صورت ناخداگاه یا نا خواسته روی برنامه نویس اول تاثیر منفی بذاره در نتیجه، وقتی کسی کدی رو بررسی میکنه باید به موارد زیر توجه داشته باشه :کسی که کد رو میخونه باید بدونه که کامنت هایی که روی اون کد میذاره، نوشته هستند و برنامه نویس اول، فقط متنو میبینه و حالت صورت یا احساسات شما رو نمیبینه در نتیجه باید با دقت نوشته بشن و حواسمون باشه که نرم بیان بشن مثلا جمله : &quot;این کد رو اینجوری بنویس...&quot; میتونه به شکل &quot;به نظرم شاید بتونیم از این کد هم استفاده کنیم، نظر تو چیه؟&quot; تغییر کنه.وقتی کامنتی میذاریم، بدونیم که کامنتها معمولا مختصر هستند و ممکنه منظورو دقیق نرسونند، اگر تونستیم حتما چیزی که میگیم یه نمونه کد هم براش قرار بدیم که منظور واضح تر بشهاگر کامنت و پاسخ ها بیشتر از ۳،۴ تا شد، بهتره بریم و به صورت حضوری حرف بزنیم چون مشخصه که منظورامونو نمیتونیم درست به هم برسونیمکد رویو ها یکی از دردسترس ترین راه ها برای یادگیری و آموزش هستند، برنامه نویس جونیور با نگاه کردن به کد های سنیور ها میتونه یاد بگیره و یا سوال هایی بپرسه و همچنین سنیور ها با نگاه کردن به کدهای جونیور ها میتونین چیزای جدید یاد بگیرن و هم به بقیه یاد بدن با کامنتایی که میذارن. در نتیجه کد ریو ها برای همه باید باشه و کاملا چرخشی باشه یعنی بین تمام اعضای تیم تقسیم بشه این وظیفهیه جاهایی نیاز به رفتو برگشت نیست، مثلا یه غلط املایی نیاز نیست گوشزد بشه، میتونیم خودمون برنچو بگیریم درستش کنیم و بذاریم بالا، فقط باید یه کامنت بذاریم که &quot;اینجا غلط املایی بود با اجازه خودم درستش کردم&quot; یا اینکه &quot;اگه اجازه بدی خودم درستش کنم&quot;... کدهایی که بررسی میکنیم باید تماما در یک مرحله بررسی بشه، یعنی اینجور نباشه که نصفشو الان بررسی کنیم و بگیم مشکلاتو برطرف کنند و بعدا نصف دیگه رو بررسی کنیم. دو دلیل داره اول اینکه وقتی کد رفتو برگشت ممکنه همونجا هایی که تغییر کرده بازم مشکل داشته باشه و دوم اینکه رفتو برگشت ها برای برنامه نویس اول کمی خسته کنندس، بهتره تمام موارد همون موقع گفته بشه تا اونم، همه رو توی یه مرحله درست کنهموارد Conventions و lint میتونن به صورت اوتوماتیک انجام بشن، گیت hook میگیره و با هر کامیت یه اسکریپت ران میکنه روی کد، اینجوری میتونین اون مواردو همون اول که در حال توسعه هست، پیدا کنین و تصحیح کنینوقتی دارین ریویو میکنین یه کانتکستی از چیزی که دارین ریویو میکنین داشته باشین، مثلا تسک جیراش رو بخونین، این کمک میکنه هم جاهای تاریک اپلیکیشن کمتر بشن، و هر بخشو حداقل دو نفر دربارش بدوننکد ریویو ها از ۱۵ تا ۱ ساعت میتونین طول بکشن که بهتره به نسبت هر تسک توی زمان برنامه ریزی و اسپرینت پلنینگ در نظر گرفته بشهاینجا یه مفهوم جالب به نام Merge Hell داریمبا Merge Hell آشنا بشیم روند PR میتونه مارو درگیر خودش کنه، چون حتی کوچیکترین تغییرات هم نیاز به PR دارند، یعنی هر تغییر یه PR میتونه باشه در نتیجه ما با حجم زیادی از PRها مواجه میشیم، این کارو میتونه سخت کنه و اصطلاحا توی جهنم این درخواستا گرفتار شین.چطور از Merge Hell فرار کنیم؟ و... PR ها باید بین تمام اعضای تیم تقسیم بشه، حتی الامکان سعی بشه که PR نه اونقدر کوچیک باشن و نه اونقدر بزرگ که بررسیشون سخت شه. PR ها رو کسی که میزنه خودشم توی توضیحاتش افرادیو منشن کنه، بر اساس سایز اون فیچر از یک تا چند نفر رو منشن کنه و همچنین این افراد میتونن از کسایی انتخاب شن که با اون بخش کمی اشنایی داشته باشن و همچنین کسی که هیچ ارتباطی با اون بخش نداشته و حتی یکی از تیم اندروید یا iOS یا تیم دیگری که اونا هم همین فیچر رو پیاده سازی کرده اندخلاصه و نتیجه گیری برای اینکه بتونیم روند PR رو نظم بدیم باید یه سری موارد رو در نظر داشته باشیمیک تمپلیت داشته باشیم که هرکسی که PR رو زد، اون موارد رو قبلش انجام داده باشه مثلا خود فرد قبلش کد هاشو Review کرده باشه، تست هاشو نوشته باشه، از نظر Code Conventions کدشو بررسی کرده باشه همچنین توی PR لینک جیرای اون تسک رو داده باشه و یه توضیح کوچیک که چطور کارشو انجام داده، اگه لینک جیرا نداره، یه توضیح کوچیک بده که اصلا این تسک قراره چه کاری بکنه تا کسی که میاد ریویو میکنه یه تصویر کلی از کار داشته باشهریویو کننده باید توی کامنتا خیلی با ادب و محتاط عمل کنه و سعی کنه همه چیزو واضح بیان کنه، بحثا نباید زیاد باشه و از گفتگوی رودرو استفاده بشه اگر طولانی شد چون هیچ متنی نمیتونه به اندازه حرف زدن مفهوم و احساسات رو برسونه و قطعا کار سریعتر پیش میرههمه تیم باید ریویو کنند و اهمیتی نداره که کدی که نوشته شده توسط سنیور ها بوده یا نه. کدها چرخشی ریویو میشن تا تیم کامل از هم خبر داشته باشند و همگی یه تصویر کلی از کارهایی که توی اپ انجام میشه رو داشته باشند.کد ریویو جایی هستش که میشه برای knowledge sharing ازش استفاده کرد، پیشنهاد من اینه که از این فرصت استفاده کنید. اگر در کامنتی اطلاعات مفیدی ردو بدل شد، کسی که PR رو ثبت کرده اون اطلاعات مفید رو توی Wiki قرار بده تا همه بخونند و اگر کسی به تیم اضافه شد راحت اون ویکی رو بررسی کنه و دیگه اشتباهات قبلیو تکرار نکنه و اون زمان حفظ بشه برای کل تیموقتی داریم برای تسک ها برنامه ریزی میکنیم، زمان Code Review ها حتما توی تایم ها در نظر گرفته بشه چون گاهی وقتا واقعا زمانگیر و انرژی بر هستندتوی کد ریویو ها، Conventions ها بررسی بشه، اگر فیچر بزرگی هستش حتما ریویو کننده اون کد رو پول کنه و روی گوشیش تست کنه تا مطمئن شه روی گوشی اونم درست داره کار میکنه، اگر کد بزرگ هستش، حداقل ۲ نفر به غیر از توسعه دهنده اون کد، اونو ریویو کنند، اگر کاریو میشه اوتوماتیک کرد حتما با CI/CD یا هوک های گیت، اونو انجام بدیم تا در زمان صرفه جویی بشه.برنامه نویس حتما اگر کد جدیدی استفاده میکند یا روشیو پیاده سازی میکند، کامنت بالای کدش بذارد که وقتی ریویو کننده مبیبنه، بتونه یاد بگیره و درکش ساده تر بشهکد ها بر اساس سایزشون میتونن از یک تا چند ریویو کننده  داشته باشند و به نسبت حساسیت نیاز به اپرومنت بیشتری برای مرج شدن دارن. کد ریویو ها کم ارزش یا بی ارزش نیستند و میتونن فرصت مناسبی برای اموزش و یادگیری و همچنین پیاده کردن باگ های احتمالی باشند و همچنین کمک میکنن که یک کد بیس یکپارچه و تمیز داشته باشیم.</description>
                <category>farshadjahanmanesh</category>
                <author>farshadjahanmanesh</author>
                <pubDate>Sun, 26 May 2019 16:54:19 +0430</pubDate>
            </item>
                    <item>
                <title> هیچ کس ۱۰۰٪ کار مفید روزانه ندارد... ادمها ربات نیستند</title>
                <link>https://virgool.io/@farshadjahanmanesh/%D9%87%DB%8C%DA%86-%DA%A9%D8%B3-%DB%B1%DB%B0%DB%B0%D9%AA-%DA%A9%D8%A7%D8%B1-%D9%85%D9%81%DB%8C%D8%AF-%D8%B1%D9%88%D8%B2%D8%A7%D9%86%D9%87-%D9%86%D8%AF%D8%A7%D8%B1%D8%AF-%D8%A7%D8%AF%D9%85%D9%87%D8%A7-%D8%B1%D8%A8%D8%A7%D8%AA-%D9%86%DB%8C%D8%B3%D8%AA%D9%86%D8%AF-obrnk6wfry20</link>
                <description>انسان یا ربات؟نیروهای کامپیوتری معمولا عاشق یادگیری هستند، دوس دارن کارهای جدید بکنن و چیزهای جدید یاد بگیرند، یکی از معضلاتی که شرکتها با اون روبه رو هستند، کارهای ساپورت و تکراری هستش. کارهایی که بابد انجام بشن، نمیشه ازشون در رفت و نمیشه نادیده گرفتشون، کارهایی که برای بقای شرکت نیازه و انجام ندادنشون صدمه جدی به شرکت میزنه، از طرفی این با خلقو خوی کامپیوتری ها سازگار نیست، کار روی پروژه های قدیمی و پر از اشکال، با ایدآل هر نیروی کامپیوتری اختلاف زیادی داره، این کار باعث میشه نیروها معمولا شرکتها رو تند تند عوض کنند ولی این عوض شدن هزینه ای برای شرکت ها داره. معمولا نیرویی که میره، قبلش شرکت جدیدش رو پیدا کرده و این بیشتر از اینکه به نیرو صدمه بزنه به شرکت میتونه آسیب بزنه، پیدا کردن نیروی با استعداد، توانا، خوش اخلاق، سریع و قوی آرزوی هر شرکتیه که با مصاحبه های فراوان سعی میکنه اونی که بیشترین نزدیکی به ایده آل هاش رو داره انتخاب کنهپس چه راهی هستش که ما بتونیم این معظل رو برطرف کنیمطبق آزمایشات و بررسی های که انجام شده (بعضی لینک ها نیاز به عبور از فیلتر دارند)https://www.inc.com:in-an-8-hour-day-the-average-worker-is-productive-for-this-many-hourshttps://medium.com:what-we-learned-about-productivity-from-analyzing-225-million-hours-of-working-time-in-2017https://www.inc.com:this-is-the-ideal-number-of-hours-to-work-a-day-achttps://www.theicpm.com:estimating-productive-hours-per-day... متوسط میزان کار مفید ۳ ساعت هستش، به نظرتون در ایران چقدره؟ همه ما میدونیم که نیروها به صورت متوسط در یک روز کاری که ٩ ساعت هستش، نهایتا ۵ ساعت کار مفید میکنن، من میدونم، شما میدونین، شرکت میدونه و رییس میدونه. یعنی در هر روز به ازای هر نفر حدود ۳ تا ۴ ساعت وقت پرت داریم که در هفته میشه بیشتر از ١٢ ساعت. این ١٢ ساعت رو همه ما میدونیم که وجود داره و هیچکس نمیتونه سعی کنه اینو کمتر کنه، یعنی کسایی که تلاش کردن تازه تونستن کار مفید روزانه رو به این عدد ۳ساعت برای هر فرد برسونن. همه این مورد رو میدونن ولی صحبت کردن یا فکر کردن بش یه قبح داره که افراد و شرکتا تصمیم میگیرن بش فکر نکنن یا نادیده بگیرنش. میتونم شرط ببندم که حتی مدیری که صاحب شرکت و محصول است یا کسی که وظیفه مدیریت ساعت کاری و پرداکتیویتی کارمندان رو دارد هم ۸ یا ۹ ساعت کار مفید انجام نمیدهد.برای بعضی نیروها زیادتر و برای بعضی نیروها کمتره. ولی چرا اینو به رسمیت نمیشناسن؟ چرا قبولش نمیکنن؟ دلیلش شاید این باشه که همه انتظار بهترین حالت رو دارن و حتی از این مورد ناراحتناگر به عوامل این زمان هدر رفته اشاره کنیم میتونیم از مقالات بالا کمک بگیریم مثلا به این عکس نگاه کنینکارهای هر فرد در طول روزیا در مقالات بالا براورد ها به این شکل بوده :خواندن اخبار و وب سایت ها حدود ۱ ساعتچک کردن شبکه های اجتماعی ۴۴ دقیقبحث و گفتگو در موارد غیرمرتبط با کار ۴۰ دقیقهجستجو برای کار بهتر ۲۶ دقیقهسیگار کشیدن ۲۳ دقیقهتماس های تلفنی ۱۸ دقیقهنوشیدن یا خوردن به غیر از ناهار ۱۷ دقیقهارسال پیامک یا چت کردن ۱۴ دقیقهغذا درست کردن در دفتر ۷ دقیقهپس ما اینجا به ازای هر نفر حداقل در هفته ١٢ ساعت وقت پرت داریم که نیرو تلف میکنه(از قصد هم نیست و این سرشت ادمی هستش که نمیتونه بیشتر از این، یه کارو انجام بده یا روش تمرکز کنه، یعنی درواقع انسان ها بر اساس ماهیت ذهنشون نمیتونن بیشتر از یه مدت، حدود ۱ ساعته روی یه چیزی تمرکز کامل داشته باشند قانون ۵۲/۱۷ رو میتونین اینجا بیشتر دربارش بخونین، بعد از ۵۲ دقیقه کار، ۱۷ دقیقه استراحت کنین تا ذهن فرش بشه)  این رو درکنار مرخصی ها، تعطیلات رسمی و ... قرار بدهید تا متوجه بشیم داستان از چه قراره.پس برای نیروهای فعلیمون به ازای هر نفر حدود حداقل ۱۲ ساعت وقت پرت در هفته داریم. هیچکس نمیتونه این ساعت ها رو کم کنه فقط باید قبولش کنیم.این داستان اولی بود که میخواستم بدونیم... از طرفی دیگهوقتی یه نیروی جدید به تیم اضافه میشه، بر اساس توانایی ها و هوش و پروژه، از ٢ هفته تا ١ ماه برای اون هزینه میشه تا پروژه رو بشناسه و خودشو با تیم هماهنگ کنه.اگر متوسط هزینه ساعتی برای یک نیرو رو حرفه ای رو در نظر بگیرم، شرکت حدود ۵٠ هزار تومان هر ساعت برای این نیرو هزینه میکنه. اگر دو هفته طول بکشه پروژها رو بشناسه، که حدود ٧٢ ساعت هزینه برای اینکار میشه به عبارتی اضافه شدن نیروی جدید حدود ٣.۵ میلیون تومان همون اول برای شرکت هزینه داره و این عدد تقریبا برای نیروهای جدید متوسط هم همینه چون اونا زمان بیشتری نیاز دارن برای اضافه شدن به تیم. از دست دادن یک نیرو قدیمی یعنی اضافه شدن نیروی جدید و هزینه های مجدد و در نهایت یعنی پول خرج کردن بیشتر. حفظ یک نیروی خوب خیلی با ارزش تر از گرفتن نیروی جدید هستش از هزینه ها گرفته تا توانایی ها... نیروهایی که شرکت رو ترک میکنن برای شرکت هزینه زیادی دارن، بخشی از دانش پروژه رو همراه خودشون میبرن، هرچی هزینه شده برای پیشرفت این نیرو و برای خوشحالی و انگیزه داشتن اون، همگی با رفتنش یه جوری سوخت میشه. تیم های بزرگ ورزشی رو نگاه کنین که برای نگهداری بازیکنانشان حاضرن دست به هرکاری بزنن در صورتیکه میتوانند اول هر فصل تمام تیم رو عوض کنند ولی ترجیح میدهند همان ها رو نگهدارند حتی به قیمت بیشتر و تنها در صورت کمبود و ضعف در یک بخش اقدام به جذب نیرو میکنند. پس از این بحث هم نتیجه میگیریم حضور و نگه داری یک نیروی خوب، خیلی با ارزش تر از گرفتن نیروی دیگر حتی خوب تر هستش.خب نقطه تلاقی و برخورد این دو داستان کجاست؟ همونجور که گفتم زمان زیادی برای هر انسان تلف میشه که شرکت موظفه چون قرارداد بلند مدت داره، هزینه این ساعت ها رو هم پرداخت کنه. از طرفی بر اساس توانایی ذهنی ادم ها، ما نمیتونیم این هزینه ها رو کم کنیم چون تمام نیروهای دنیا همینجوری هستند، چون ادم ها ربات نیستند که ۱۰۰ یا نزدیک به ۱۰۰٪ پروداکتیو باشند. خب شرکت داره این هزینه رو میکنه ولی از این ساعت های پرت چیزی نصیبش نمیشه.از طرفی گفتم که نیروهای کامپیوتری عاشق یاد گیری هستند و همیشه مشتاق برای یادگیری چیز های جدید و تکنیک های جدید هستند.چرا نیایم و از این هزینه که بخوایم نخوایم باید انجام بدیم سودی هم ببریم؟ میتونیم به نیروها ساعت های مشخصی رو اجازه بدیم استراحت کنند، شبکهای اجتماعی رو چک کنند، با تلفن حرف بزنن، حرفای غیر مرتبط با کار بزنن... وقتی نیروها بدونن ساعت های تنظیم شده ای برای این موارد هست، میتونن مدیریت کنند کارهاشون رو، دیگه وسط یه تسک به شبکه های اجتماعی سر نمیزنند، میدونن ساعت تنظیم شده ای برای این کار هستش. از طرفی میتوینم بشون بگیم توی یه ساعت ها یا روزهایی از هفته مطالعه ازاد یا تکنولوژی جدیدی رو یاد بگیرن (بازم باید بگم این ساعت ها بخوایم نخوایم هزینه میشه چون انسان ها ۱۰۰٪ پروداکتیو نیستند) ما میتونیم از این ساعت ها به عنوان یه سوپسیت و هدیه به نیروها استفاده کنیم و برای خودمون اعتبار بخریم.حالا سود از کجا ببریم؟ وقتی نیروهامون حرفه ای تر بشند، سرچ هاشون کمتر میشه، کدها سریعتر زده میشن، باگ ها کمتر میشه و محصول نهایی با کیفیت تر میشه. اگر یه نیرو متوسط بگیرم و تا اخر حضورش همون نیرو قبلی با توانایی های قبلی بمونه، سود و زیانش سر به سر شده یعنی کار کرده پول گرفته ولی ارزش افزوده ای برای ما نداشته.وقتی نیروهای حرفه ای و قوی داشته باشیم متونیم سمینار برگزار کنیم و این نیروها اموزش بدن و از سمنیار پول بگیریممیتونیم ویدیو های آموزشی درست کنیم و از فروش اونها پول دربیاریم. میتونیم کتاب بنویسیم. میتونیم از نیروها بخوایم که دانششون رو به بقیه انتقال بدن. میتونیم با نیروهای حرفه ای برندسازی کنیم و برند خودمون رو قوی تر کنیم. میتونیم با این امتیازی که (حتی ناچارن و اجبارا) داریم به نیرو میدیم استفاده کنیم و لویالیتی اون نیرو رو بدست بیاریم... با اینکار نه تنها یکی از بزرگترین معضلات نیروها رو برطرف میکنیم بلکه از بی انگیزه شدنشون هم جلوگیری. بازم تیترو تکرار میکنم  هیچ کس ۱۰۰٪ کار مفید روزانه ندارد... پس من به عنوان یه شرکت میتونم از این استفاده کنم .</description>
                <category>farshadjahanmanesh</category>
                <author>farshadjahanmanesh</author>
                <pubDate>Wed, 09 Jan 2019 15:11:30 +0330</pubDate>
            </item>
                    <item>
                <title>اسکرام... خوب، بد، زشت...</title>
                <link>https://virgool.io/@farshadjahanmanesh/%D8%A7%D8%B3%DA%A9%D8%B1%D8%A7%D9%85-%D8%AE%D9%88%D8%A8-%D8%A8%D8%AF-%D8%B2%D8%B4%D8%AA-hts0a8m8bivn</link>
                <description>Scrumوقتی از متد های اجایل صحبت میکنیم اکثر بحث ها به اسکرام ختم میشه.  اسکرام یک سری پند و اندرز داره برامون که میگه اگر به اینها عمل کنین، رستگار میشین. داستانش از اونجایی شروع میشه که...روزی روزگاری یه شرکت بزرگ بود که با مشکل ناهماهنگی کارکنان، نرسیدن به ددلاین های پروژه، نامنظمی کارمنداش دستو پنجه نرم میکرد، یه شب مدیر تیم اپلیکیشن با ناراحتی به خونه میرسه، وسایلشو میذاره روی زمین و خوابش میبره... چشماشو باز میکنه، ولی تار میبینه اطراف رو،یه برگه کهنه که جلوش افتاده نظرشو جلب میکنه، روی برگه نوشته شده &quot;SCRUM&quot; ... بازش میکنه که یه دفعه نوری از درون برگه میزنه بیرون و همه جا رو روشن میکنه به قدری که محیط اطراف همه سفید میشه و بعد مدیر تیم خودشو توی محیطی میبینه که همه خوشحالن، همه دارن کار میکنن، همه پروژه ها منظمه، همه ددلاین ها ساکسز شدن... نور محو میشه و ۵ جمله روی اون برگه میبیینه و بالای برگه نوشته، &quot;برای آنان که فکر میکنن&quot;...تیم کاملا Self-Organize است. هیچ کس نه از بیرون و نه از داخل به تیم نمیگه که یک کار رو چطور به اتمام برسون. تیم بر پایه اعتماد به یکدیگر جلو میره و شرکت کاملا به هوش توانایی و دانش فنی تیم اعتماد میکنه.در اسکرام نباید بشنوییم که میگیم تیم اپ، تیم گرافیک، تیم تست. همه تیم ها دارن با هم کار میکنن و به هم سرویس میدن تا یک محصول نهایی تولید شود. اگر نیاز های یکی از این تیم ها براورده نشود یعنی مسیر درستی نمی رویم. در گذشته تیم ها یکی بعد از دیگری کار را شروع میکردند. اول تیم طراحی بعد توسعه بعد تست بعد فروش و ...همه جلسات و هماهنگی های اسکرام رو باید سعی کنیم همیشه در جایی ثابت و ساعت ثابت و از قبل هماهنگ شده برنامه ریزی کنیم تا از تلف شدن وقت جلوگیری بشهمدیر محصول به عنوان تصمیم گیرنده نهایی قرار میگیره و همه تصمیمات درباره اینکه چه چیزی باید در محصول قرار بگیره یا نه و پاسخ دهنده نهایی است.در اسکرام هیچ عنوانی روی توسعه دهنده ها قرار نمیگرد. این سلسله مراتب بودن جلو گییری میکنه و همه اعضایی تیم رو وادار میکنه به طور کامل درون تیم و کارها مشارکت کننداین ها کلیات هستند ولی در عمل چه اتفاقی میوفته؟ تجربه واقعی میگه که همه در تیم مشارکت نمیکنند. همه تلاش واحد و یکسانی ندارند. ایجاد اشتیاق برای کسی که داره زیاد تلاش میکنه با کسی که معمولی قدم بر میداره سخته و حفظ تعادل پیچیده میشه.  اگر بخوایم قدم قدم بریم اینجوری اسکرام رو پیاده سازی میکنیم. ما اینجوری اسکرام رو پیاده سازی کردیماول ما به یه تیم نیاز داریم، دو نفر یا بیشتر نیرو...مرحله دوم انتخاب Product-Owner هستش. ما یک نفر به نام Product-Owner داریم. این نقش(در تیم) وظیفه ارتباط با بیرون، تهیه نیازمندی های تیم برای انجام یک تسک و تحویل گرفتن اون تسک بعد از تموم شدن رو داره. ولی مهمترین وظیفه اینه که تیم برای تصمیم هایی که نمیتونه بگیره یا راهی که نمیدونه الان باید دقیقا کدوم رو انتخاب کنه به یک تصمیم نهایی داره. کسی که حرف نهایی رو روی تسک هایی که ابهام دارن بزنه. این وظیفه مدیر محصول هستش.کارها توسط مدیر محصول مشخص میشن و اولویت ها بررسی میشند. توی اسکرام ما اسپرینت داریم، یعنی برای مثال روز اول هفته میشینیم و کارهای دو هفته اینده رو در میاریم و شروع به انجامشون میکنیم. مدت زمان اسپرینت ها معمولا با توجه به ماهیت پروژه تعیین میشن. در نتیجه میتونن هفتگی، دو هفته یا ماهانه باشند ولی معمولا کمتر از یک هفته نمیتونن باشن. پس اسپرینت چیه؟ یه بازه زمانی مثل یک هفته یا چند هفته، که از قبل کارهایی که باید تو این مدت انجام بشه رو در میاریم و میگیم اخر اسپرینت باید این کارها تموم شده باشند. یکی از دلایل جذاب برای اینکه اسپرینت داشته باشیم اینه که ما یه کار بزرگ (ساختن یه پروژه) رو به کارهای کوچیک تقسیم میکنیم، اسپرینت علاوه بر این، اولویت ها رو هم برامون در میاره یعنی شما توی هر اسپرینت میدونین چه چیزی از همه مهمتره و باید اول انجام بشه، شما کلی تسک دارین که مشت مشت (اسپرینت اسپرینت) برشون میدارین، دسته بندی میکنین و انجامشون میدین.پس مرحله سوم میتونه این باشه که پروژه رو بشناسیم و تعیین کنیم که هر اسپرینت ما چند هفته باشه. ما دو هفته ای اسپرینت ها رو میبندیم.بعد از این باید بیایم سراغ کارهایی که باید انجام شه. کارها واحد هایی از پروژه هستند که باید انجام شن. ساخت لاگین، ساخت صفحه پروفایل و ... ما یه سبد داریم که تسک ها رو میریزم توش، مثل یه فایل در نظر بگیرین که همینجوری تسک هارو بش اضافه میکنیم. یه گونی، سبد یا هر چیزی و به اون بکلاگ Backlog میگیم. بکلاگ شامل همه کارهاییه که باید انجام بشه. روز اول ما همه کارهارو نمیدونیم. هرچی میدونیم رو به بک لاگ اضافه میکنیم و هرچی که در اینده به ذهنمون رسید، مشتری خواست یا باگی ایرادی چیزی دیدیم به بک لاگ اضافه میکنیم. همه تیم میتونن به این بکلاگ کار اضافه کنند. پس قدم چهارم میتونه این باشه که یه لیست از کارهایی که باید انجام بشه در بیاریم مهم نیست که همه کارها رو بدونیم یا همه رو از اول به بکلاگ اضافه کنیم. هرچی که میدونیم رو اضافه میکنیم و در اینده هرچی نیاز بود بازم میریزیم تو سبد بکلاگمون.قدم پنجم اینجاست که Product-Owner باید بیاد و بررسی کنه. بکلاگ رو چک میکنه، با مشتری یا هرکسی دیگه ای که باید، چک میکنه و در نهایت تسک ها رو اولویت بندی میکنه یعنی اونایی که باید سریعتر انجام بشن میان بالای لیست، اینکار به صورت مداوم انجام میشه و هروقت فرصت میکنه اینکارو باید انجام بده، لیست رو اپدیت میکنه.خب شما کارهایی که باید انجام بدین رو دارین (بکلاگ) اولویتشون هم که مشخص شده، اینجا تیم باید برای اسپرینتشون برنامه ریزی کنه. چه کارهایی رو باید توی این اسپرینت انجام بده. تیم دور هم جمع میشه و جلسه اسپرینت میذاره، کارهایی که باید انجام بده رو مشخص میکنه.پس قدم بعدی (۶) برگذاری جلسه اسپرینت هستش. کسایی که باید توی این جلسه باشن تیم و پروداکت اونر حتما باید باشن. ما اینجا بر اساس تعداد اعضای تیم کارها رو بر میداریم و توی اسپرینتمون میذاریم. مثلا میگیم این ۱۰ تا کارو باید توی این دو هفته (مدت اسپرینت) انجام بدیم. از کجا میدونیم که ۱۰ تا کار رو میتونیم انجام بدیم توی دو هفته؟ راستش... اول کار نمیدونیم. ولی کم کم متوجه میشیم که تیم توی هر اسپرینت چندتا کار میتونه انجام بده. ولی کارها همه از یک جنس نیستن یعنی همه یه سایز ندارن. مثلا ساخت صفحه لاگین و کار تغییر متن ؛سلام؛ به سلام بر شما... هر دو یه مقدار زمان نیاز ندارند پس اینکه چنتا کار توی یه اسپرینت میشه انجام داد به دو عامل بستگی داره :‌توانایی و سرعت تیمبزرگی یا کوچکی کارهاپس ما باید یه راهی پیدا کنیم که ببینم توی این اسپرینت چنتا کار میتونیم انجام بدیم. اینجا مفهومی به نام  استوری پوینت Story Point داریم. این یه مقیاس از سایز کاری (از نظر زمانی) که باید انجام بشه و پیچیدگی اون  کار هستش. یعنی مثلا فرض کنین ما ساخت صفحه لاگین رو داریم. باید ببینیم چقدر کار داره ولی خب ما عدد دقیقی نمیدونیم. میایم بش Story Point میدیم. چطور؟ اینجا با یه مفهوم دیگه به نام پوکر پلنینگ Poker Planning اشنا میشیم.گفتیم توی جلسه اسپرینت، تیم هستند. تسک رو بر میداریم و از تیم میخوایم استوری پوینت بدن. یعنی هرکدوم از اعضای تیم بگن که اینکار چقدر پیچیده هستش. اینکار مثل پوکر انجام میشه. یک دو سه، همه اعضای تیم با هم استوری پوینتی که به این کار دادن رو نمایش میدن مثلا ۱،۲،۳...۱۰۰. معمولا به صورت استاندارد ۱۰۰ بالاترین استوری پوینت هستش و هرچی عدد بزرگتر بشه، از نظر تیم این کار پیچیده تر و زمان برتر است. کارو میزنیم به تخته و استوری پوینت رو روش مینویسیم. با اینکار متوجه میشیم که این کار چقدر پیچیده هستش . کار بعدی رو از بالای بکلاگ بر میداریم و بازم امتیاز گیری میکنیم. راستش اسپرینت های اول نمیدونیم که تیم چند استوری پوینت توی یه اسپرینت میتونن انجام بدن. در نتیجه بر اساس حدسی که میزنیم چنتا کارو برای انجام توی اون اسپرینت بر میداریم. وقتی استوری پوینت ها رو دادیم حالا از تیم میخوایم که بگن به نظرشون اینکار چقدر زمان میبره. دقیقا به ساعت یا روز بگن که حدس میزنن هرکدوم از این کارها چقدر زمان میبره این زمان دادن رو هم به صورت پوکر انجام میدیم. چرا باید همه تیم با هم و همزمان عددهایی که توی ذهنشون دارن رو بگن؟ برای اینکه رای یه نفر روی بقیه تاثیر نذاره. مثلا یکی که فک میکرده کار اسونی ولی یه نفر میگه خیلی سخته و در نهایت نفر اولم میگه شاید من اشتباه میکنم. کلا استوری پوینت دادن و تخمین زمانی از اسمشونو پیداست. عدد دقیقی نیستند و فقط و فقط برای تخمین زدن هستن. تیم بعد از گذشت چند اسپرینت متوجه میشه که هر کار تقریبا چقدر زمان میخواد و استوری پوینت و زمانی که به یه تخمین مناسب از استوری پوینت و زمان رسیدیم میتونیم جلسه اسپرینت رو سریعتر پیش ببریم و دیگه فقط استوری پوینت بدیم و زمان رو براساس اون تخمینی که بدست اوردیم حساب کنیم. مثلا بعد از ۵ اسپرینت متوجه میشییم که هر ۱۳ استوری پوینت حدود ۱ روز کار میبره یعنی ۸ ساعت در نتیجه هر استوری پوینت ما حدود ۴۵ دقیقه هستش. اینجوری ما یه ویو کلی از تیممون و تواناییشون پیدا میکنیم. اینجوری میتونیم یه تخمین صحیح داشته باشیم و روش برنامه ریزی کنیم. بعد از اینکه کارهایی که باید انجام بشن مشخص شد، Product-Owner میاد و همون تسکهای مربوط به اون اسپرینت رو هم اولویت بندی میکنه یعنی اونایی که اولویت بالاتری دارند، سریعتر باید انجام بشنپس هدف بعدی مون اسپرینت و پیدا کردن کارهایی شد که باید توی اون اسپرینت انجام بدن.این جلسات برگزار میشه و کم کم، مشت مشت تسک از توی بکلاگ بالا میاد و انجام میشه تا پروژه تمام و تمام بکلاگ خالی میشه. وقتی کارهای دو هفته مشخص شد، تیم دیگه میتونه کار خودش رو شروع کنه، بدون اینکه به کسی نیاز داشته باشه. تسک ها رو توی جیرا یا هر نرم افزاری که برای مدیریت پروژه داریم میزنیم. خب اگر تیم بزرگی داریم مثلا ۳ یا بیشتر، جلسه صبحگاهی روزانه رو فراموش نکنیم. هروز صبح سر یه ساعتی که همه میدوونن مثلا ۱۰، پاشیم و درباره کارهایی که امروز میخوایم بکنیم و فردا کمی حرف بزنیم. این خیلی کاربردی و خوبه چون اول اینکه تیم متوجه میشه چه کاری داره انجام میده و دوم اینکه تک تک افراد در جریان کارهای همه تیم هستند و حتی شاید بتونن کمک کنند. این ویژگی از تداخل ها یا اشتباهات کوچیک یا بززرگ تا حد زیادی جلوگیری میکنه. جلسات صبحگاهی رو سرپا برگذار کنیم. چرا؟ وقتی سر پا باشیم، خسته میشیم و این خسته شدن کمک میکنه تا سریعتر جلسه رو تموم کنیم. یعنی از اتلاف وقت و گفتگو درباره چیز های بی مورد جلوگیری میکنه ولی همیشه برگزارش کنین. این جلسه اصلا برای اینکه هرکسی رو زیر نظر داشته باشیم نیست و بیشتر برای اینه که تیم از حال هم با خبر بشه.اخر هر اسپرینت دوباره جلسه میزاریم و تسک های اون هفته رو تحویل  Product-Owner میدیم. ولی بهتره هر تسکی که تموم شد تحویل داده بشه تا اگر ایرادی داره همون موقع گفته بشه و اخر هفته تسک های دان شده کامل رو تحویل میدیم . بعدش درباره این اسپرینت صحبت میکنیم و سعی میکنیم بدی و خوبیاش رو بگیم. چه چیزی باعث شد سریعتر پیش بریم؟ چه چیزی ما رو کند کرد؟ اگر چه اتفاقی میوفتاد بهتر بود و اگر چه اتفاقی نمیوفتاد. یه گفتگو دوستانه برای اینکه بتونیم اسپرینت بعدی بهتر باشیم.یه نقشی هم داریم به نام اسکرام مستر Scrum Master، این نقش توی تیم وظیفه یاد دادن اسکرام و جا انداختنشو داره. این نقش از دور به اسکرام نگاه میکنه و اگر نیاز بود نزدیک میشه و تیم رو راهنمایی میکنه برای اینکه بهتر اسکرام رو پیاده سازی بکنن. ایده و همه ارزوی اسکرام مستر، اینه که تیم رو سلف اورگنایز کنه Self-Organize کنه. اسکرام مستر حرفها رو میشنوه، اگر نیاز باشه به تیم کمک میکنه، سعی میکنه تک تک اعضای تیم رو SelfOrganize کنه. Self-Organize یعنی چی؟ هرفرد در تیم نیاز داره خودش رو مدیریت کنه، اصطلاحا تیم ها در اسکرام فلت هستند و نقشهایی که بودن مثلا Team Leader و ... کم رنگ یا حذف شدند. هر عضو از تیم باید بتونه خودش و بقیه رو مدریت کنه، هر نفر بدونه چیکار میخواد بکنه، چیکار باید بکنه و مسولیت کارهاشو برعهده بگیره، توی تصمیم گیری ها شرکت کنه و خودش رو به اندازه همه اعضای تیم مسول و تاثیر گذار بدونه. اسکرام مستر یکی یکی از اعضا رو تلاش میکنه Self Organize کنه و وقتی تیم به این ویژگی رسید، دیگه نیاز به ناظر نداره، خودش تسک هاش رو بر میداره، خودش جلسات رو برگزار میکنه، خودش برای پیشبرد پروژه تلاش میکنه. رسیدن به این ويژگی کار پیچیده ای هستش و سخت است چون افراد و اعضای تیم همگی در یک حد نیستند و در نتیجه سخته همه رو به سرعت Self Organize کرد. مطالبی که بالا گفته شد الان درحال انجام هستش روی تیم ما. اگر بخوام بگم اسکرام چه کمکی به ما کرده میتونم به این اشاره کنم که ما هرکدوم میدونیم که باید چه کاری بکنیم و کارها چطور تقسیم شدن. ما همه میدونیم که توی هر اسپرینت باید به کجا برسیم. میتونیم وقت هامونو رو تنظیم کنیم و همچنین ببینیم که اگر وقت خالی داریم اونو مدیریت کنیم با کارهای جانبی. نقش های مخفی در اسکرامایا همه تیم شما از یک دانش و سطح توانایی برخوردارند؟ معمولا اینجور نیست. ما همیشه نمیتونیم ۱۰ سنیور دولوپر در کنار هم داشته باشیم چون هزینه تیم خیلی بالا میرود در نتیجه ترکیبی از سنیور ها و جونیور ها داریم. در اسکرام به فلت بودن تاکید میکنیم ولی در واقعیت نمیشه اینجور جلو رفت. من به شخصه اعتقاد دارم حتی اگر این اسم ها حذف شدند، ولی وجود این نقش ها در تیم کلیدی هستش. معمولا باید افرادی باشن که کد ها رو ریویو کنند، به تیم کمک کنند، از نظر دانشی سوالات رو پاسخ بدن و راهنمایی کنند. وقتی یکی اشتباه میکنه ما تیم رو تنبیه میکنیم ولی ایا بقیه تیم به همون اندازه که اون فرد اشتباه کننده، ناراحت شده، تحت تاثیر قرار میگیره؟ وقتی من مسئول کدهای خودم هستم آیا به اندازه کسی که اشتباه کرده خودمو سرزنش میکنم؟ آیا وقتی تیم فلت هستش کسی از دیگری سوالی میپرسه؟ اگر  یکی از اعضا براش اهمیت نداشت و یکی براش اهمیت داشت چه اتفاقی میوفته؟ اگر یه عده کارنکنن و یکی از ترس اینکه کارها بمونه، کارهای بقیه رو انجام بده چی میشه؟ اعضای تیم ها همگی باید یک دست باشند در غیر اینصورت همیشه یه ناظر نیازمند هستش. Team Leader یکی از نقش هایی هستش که در اسکرام حذف شده، team leader ها وظیفه راهنمایی تیم برای بالابردن کیفیت محصول ارایه شده از نظر فنی رو دارند. تیم رو به مسیر درست هدایت میکنند. انتخاب صحیح تکنولوژي، انجام بعضی Code-Reviewها، پاسخ به سوالات تیم، انجام و پیاده سازی صحیح تکنیک ها، این افراد تیم رو بهتر میکنند. وقتی یه عنوان یه مرجع شناخته بشن و تایتلش رو حمل کنند، تیم همیشه میتونه سوالاتشو رو بپرسه ولی اینکه ما بگیم فلت در نتیجه هرکسی برای خودش تصمیم میگیره و پیاده سازی میکنه و نهایتا یه نظر میخواد ولی کار اصلی رو خودش میکنه، این خوبه ولی نمیتونیم تضمین کنیم که بهترین راه رو داره میره. من خودم صرفا با فلت بودن مخالفم و به نظرم این نمیتونه به تیم کمک کنه که محصول با کیفیت تری بده، میتونه کمک کنه تیم مسولیت پذیر تر شه، ولی نمیتونه کمک کنه کیفیت بالاتر بره. چون برای انجام یه کار، راه های متفاوتی وجود داره ولی هرکسی به اندازه دانش علمیش، اون راه ها رو بلده و نمیشه تضمین کرد که همه بهترین کارو میکنن. فلت بودن تنها زمانی امکان داره که هم از نظر دانش فنی در یک سطح یا نزدیک به هم باشن.شاید اسم این رولی که من بش اشاره میکنم Team Leader نباشه ولی دقیقا دارم به تعریف صریحش توی ویکی پدیا اشاره میکنمA team leader is someone who provides guidance, instruction, direction and leadership to a group of individuals (the team) for the purpose of achieving a key result or group of aligned results. The team leader monitors the quantitative and qualitative achievements of the team and reports results to a manager (a manager may oversee multiple teams). The leader often works within the team, as a member, carrying out the same roles but with the additional &#039;leader&#039; responsibilities من دارم به کسی اشاره میکنم که تیم برای پرسش های علمی، راهنمایی برای استفاده از یک تکنولوژي، به عنوان یک مرجع برای حل یک مشکل بش اشاره کنه. همیشه در کنار تیم هستش و درکنار تیم هستش و  درکنارشون کد میزنه. وقتش کامل در اختیار تیم هستش، در جلسات خارج از تیم شرکت نمیکنه. این فرد میتونه به تیم کمک کنه که پیشرفت کنه. چرا نیاز است؟ فرهنگ سازی برای ما سخته، قبول اینکه یه نفر از ما بهتر هستش سخته. کم پیش میاد سوالی پرسیده بشه، مخصوصا توی تیم های برنامه نویسی که همه اطلاعاتشون رو سریعا توی stackOverflow جستجو میکنن و فکر میکنن مشکل رو حل کردن در صورتیکه الزاما اون نتیجه بهترین گزینه نیست. راه حل ها زیاده ولی همیشه همه بهترین نیستند. من هدفم اینه که کدهایی که زده میشه بالاترین کیفیت رو داشته باشند. محصولی که ارایه میشه در سطح مناسبی باشه و نگهداری از اون راحت باشه. چند نفر از ما با پروژه های ضعیف و کثیف مواجه شدیم؟ چند نفر از ما با اعتماد به نیروها جلو رفتیم و در نهایت پروژه ای با کیفیت بسیار کم داشتیم؟ چند تا تسک کد ریویو  داشتیم و انجام نشده؟ کد ریویو وقتی که ۲۰۰ خط کد زده شد چه فایده ای داره؟ ایا شما به یکی میگی همه رو از اول بزن وقتی ۱ هفته روش کار کرده؟ اگر همون اول سوال پرسیده میشد و درست جلو میرفت هزینه کمتری داشت یا بعد از اینکه ۱ هفته گذشته و شما تازه کد ها رو میبینین؟ انسان ها به عنوان احترام زیادی میذارن. اگر رولی به نام Product Owner نبود، آیا شما به کسی مراجعه میکردین برای سوالاتون یا نهایتا با بغل دستی مشورت میکردیم و تمام؟ اگر رولی به نام مدیر نبود آیا از هم سطح خودتون کمک میخواستین یا فکر میکردین که این کار ضعف من رو میرسونه؟ اگر یکی باشه که همه ازش سوال کنند آیا سوال کردن از اون شخص ضعف شما رو میرسونه؟ از تیم های ورزشی، مفهومی بالاتر از تیم هم داریم؟ ۱۱ نفر با هم همکاری میکنن و مفهوم کامل تیم هستند، هر تیم یه کاپیتان داره که پا به پاشون تلاش میکنه، مدیر همش توی جلسه هستش، نمیتونه به عنوان یک مرجع در دسترس باشه، چقدر مدیریتون در روز کنارتون هستش؟ چقدر درجریان نحوه کد زدن ها و پیاده سازیشون هستش؟ هر اسمی روش بذاریم، به نظر من یه نفر در هر تیم باید مرجع باشه پا به پای بقیه بدوه و بقیه بتونن بدون ترس از اینکه نکنه ضعیف باشیم، بش رجوع کنند.</description>
                <category>farshadjahanmanesh</category>
                <author>farshadjahanmanesh</author>
                <pubDate>Mon, 07 Jan 2019 16:24:40 +0330</pubDate>
            </item>
                    <item>
                <title>راه های رسیدن به GitFlow</title>
                <link>https://virgool.io/@farshadjahanmanesh/%D8%B1%D8%A7%D9%87-%D9%87%D8%A7%DB%8C-%D8%B1%D8%B3%DB%8C%D8%AF%D9%86-%D8%A8%D9%87-gitflow-my2yaqt0d6dh</link>
                <description>مشکل بزرگ ما و ضربه بدی که خوردیم چی بود؟همیشه راه حل ها از مشکلات ساخته میشن. همونجور که از اسمشون پیداست راهی برای حل کردن یک مسئله. ماجرا از جایی شروع شد که ما با یک مشکل بزرگ روبه رو شدیم. اپلیکیشنی که پابلیش شد، حاوی یه سری فیچر بود که در حال توسعه بودند. یعنی هنوز کارمون با اونا تموم نشده بود ولی در دسترس تعداد زیادی کاربر قرار گرفت و کلی مشکلات به وجود آورد از جمله که کارفرما یکی از این فیچر ها رو خیلی رقابتی میدونست و حالا دیگه رقیب ها هم میدونستن که قراره چی بیاد توی ورژن بعدی. امیدوارم اهمیت مسئله رو خوب بیان کرده باشم. از اونجایی که اکثر ماها سعی میکنیم مشکلی پیش بیاد تا بعد رفعش کنیم و به جلوگیری اعتقادی نداریم این موارد پیش میاد. در نتیجه تصمیم بر این شد این مقاله رو بنویسیم تا کسایی که هنوز با مشکلاتی شبیه چیزی که ما تجربه کردیم مواجه نشدن، بخونن و به فکر پیشگیری بیوفتن.اگر بخوام مثال های دیگه ای برای اینکه چرا ما به یک روند واحد برای مدریت گیت پروژه هامون نیاز داریم  بزنم میتونم به ریلیز بعضی از فیچرهای در حال توسعهنداشتن برنچ امن و پایداری که در هر زمان بشه به اون رجوع کردنمیشه به راحتی روند انجام یک کار رو بررسی کرد و شاید یه کارهای انجام شده رو به حالت قبل برگردوندهمه دولوپر ها به همه برنچ ها دسترسی دارند و درنتیجه کانفلیکت ها، باگ های عیجب غریب پیش میادچرا GitFlow؟ اصلا Gitflow چیه؟	توی دنیا، از شرکت های خیلی کوچیک تا بزرگ برای نگه داشتن کدهاشون، توسعه اون ها و مدیریتشون از ابزارهای خاصی استفاده میکنند. بعضی ها پروژه رو به صورت یه فایل زیپ بین هم جابجا میکنن و بعضی هم پیشرفت کردند (که اکثرا دیگه میشه گفت ۹۹٪ شرکتها) و از گیت برای مدیریت پروژه هاشون استفاده میکنند. اینجوری در هر زمان افراد مختلف میتونن روی کدها کار کنند، تغییرات هم رو ببینین، تاریخچه کدها رو داشته باشن، محیط امنی فراهم کنند تا از اتفاقات ناخواسته جلوگیری کنند و خیلی موارد دیگه. قطعا اگر دارین این مطلب رو میخونین درباره گیت میدونین ولی اگر احیانا نمیدونین میتونین از این لینک اطلاعات خوبی درباره گیت بدست بیارین.	دقیقا GitFlow چیکار میکنه؟ شرکت ها برای اینکه هماهنگی بین تیمشون به وجود بیارن، میان و یک روند استاندارد برای تیمشون تعریف میکنن تا همه اعضای تیم دقیقا بدونن که چه طور برنچ جدید درست کنند، چطور فیچر اضافه کنند، باگ فیکس ها رو چطور مدیریت کنند، خروجی ها و ریلیز ها چطور مدیریت میشه روی گیت اون شرکت. روشهای استانداردی برای اینکار وجود داره مثلا گیتهاب و گیتلب روش های پیشنهادی خودشون رو گفتن و حتی یک مقاله خوب هم دراین باره نوشته شده که میتونین در اینجا مطالعه کنین و خیلیها هم دارن به همون روش ها جلو میرن، ولی این روش ها همیشه و الزاما برای همه بهترین گزینه نیستند، چون همونجور که اول مطلب گفتیم، اول مشکل پیش میاد بعد راه حلش، در نتیجه این مطالب هرچند فراگیر باشند و بتونین جامعه زیادی رو پوشش بدن، فرض کنیم ۹۰٪ جامعه رو پوشش بدن، ولی همیشه هستند شرکت و تیم هایی که این روشها نمیتونن نیاز هاشونو برطرف کنند، شاید شما و ما هم یکی از اون ۱۰٪ باشیم.بهتره اول روش عمومی و پیشنهادی رو بیان کنمروش استاندارد GitFlowStandard Git Flowتوی این روش ما دو برنچ اصلی Master و Develop داریم، همه دولوپرها ملزم به استفاده از برنچ Develop به عنوان برنچ اصلی هستند و تنها زمانی که یک کد ریلیز میشه، کدهای اون ریلیز روی مستر push میشه. برنچ دولوپ از مستر ساخته میشه و همیشه حضور داره و هیچوقت پاک نمیشه، دولوپر ها همه کارهاشون روی این برنچ انجام میدن. زمانیکه نیاز به ریلیز باشه، یک برنچ ریلیز از برنچ دولوپ گرفته میشه اون کدها ریلیز میشن و در نهایت برنچ ریلیز با مستر merge میشه و کدهای اون ریلیز روی مستر قرار میگیره. برنچ دولوپ اینجور مدیریت میشه که برای هر فیچر جدید که قراره به اپلیکیشن اضافه بشه دولوپر ها یک برنچ از روی Develop میسازن و روی اون برنچ جدید کارهاشونو انجام میدن و وقتی تموم میشه push میشه و در نهایت اون برنچ حذف میشه. این روند استاندارد هستش و خیلی وقت ها تمام نیاز ها رو جواب میده هیچ ایرادی نداره به صورت پیشفرض همگی از این روش استفاده میکنیم ولی چون روش استاندارد هستش باید یه سریی چیز ها برای سازگاری با محیط ایران به اون اضافه کنیم.ما چرا باید به روند استاندارد که بالا گفته شد چیزی اضافه کنیم؟همینجوری که همه میدونیم، ایران خیلی چیزهاش شبیه بقیه دنیا نیست، معمولا روشهایی که روی همه کشور ها جواب میده با توجه به وضعیت اقتصادی، سیاسی، فرهنگی و شخصیتی ایرانی ها، روی ما جواب نمیده. اگه بخوام به یکی از این موارد و معضلات اشاره کنم، اینه که نه تیم فنی و نه کارفرما، برنامه ریزی دقیقی ندارند و در واقع بیشتر کارفرما بجای اینکه از روی یه پلن از پیش تعیین شده بخواد جلو بره، به صورت لحظه ای تصمیم گیری میکنه و در نتیجه تیم فنی نیاز به هماهنگ شدن دارند، این معضل با توجه به شرایط سیاسی و اقتصادی ایران، کارفرما رو مجاب میکنه که بجای برنامه ریزی بلند مدت، تصمیم به انجام کارهای کوچیک کوتاه مدت و مقتضی اون زمان بکنه، در نتیجه تیم باید اینقدر چابک باشه تا بتونه با سرعت به تغییرات مورد نیاز کارفرما و درخواست های جدیدش رسیدگی کنه. از اونجایی که همچین وضعیت هایی خیلی کمتر توی شرکتهای اروپایی و امریکایی پیش میاد، در علمی که اکثرا از اون سمت به وجود میاد، این شرایط نادیده یا کمرنگ تر در نظر گرفته میشه و شاید راه حل ها و پیاده سازی های اونها در بعضی موارد با نیاز های ما توی ایران سازگار نباشه. ما در روند فوق، ایراد هایی دیدیم که شاید مقتضی شرایط کاری ما باشه و احتمالا به خیلی های دیگه در ایران میتونه کمک کنه. ما میخوایم به این مسائل پاسخ بدیم:۱. ما میخوایم که Master، حاوی کد های اصلی و استیبل و پایدار برنامه باشه و هرکسی که به تیم اضافه شد یا حتی از بیرون اومد، بدونه اینو و مستر همیشه و در همه حال آماده خروجی گرفتن و ریلیز هستش. دولوپر ها به این برنچ دسترسی نداشته باشه۲. خیلی وقت ها شده که ما میخوایم یه لیبل یا رنگ یک دکمه یا ارتفاع یک ستون یا موارد ساده کوچیکی مثل اینها رو برطرف کنیم ولی این ها نباید مستقیم روی برنچ مستر انجام بشه حتی اگر یک ثانیه کار داره۳. مشکلاتی مثل Merge Hell رو باید پاسخ بدیم. Merge Hell در دو حالت به وجود میاد، زمانیکه تعداد درخواست های مرج خیلی زیاد باشه و یا اینکه موارد تغییر کرده در یک درخواست اینقدر زیاده که کسی که در حال بررسی این درخواست هستش نمیتونه دقیق پیش بره و کارش خیلی سخت میشه برای بررسی این درخواست۴. بعضی وقت ها فیچر هایی به اپ اضافه میشه که نمیخوایم همون موقع در خروجی قرار بگیره یا در ریلیز بعدی باشه، ممکنه زمانی مثلا ۳ یا ۴ ماه بمونه و ریلیز نشه۵. گاهی وقتها چند نفر روی یک برنچ کار میکنن یا چند نفر روی چند برنچ کار میکنن این باید مدیریت بشه۶. گاهی وقت ها نیازه که در همون لحظه یک باگ برطرف بشه و خروجی گرفته بشه بدون اینکه فیچر های جدید درون اون ریلیز قرار بگیرند۷. ما نیاز داریم که قبل از ریلیز نهایی که دست کاربران قرار میگیره، خروجی کاملا تست بشه و کل اپلیکیشن یکبار توسط تیم تست بررسی بشه.۸. فیچر ها تا قبل اینکه تمام بشن به هیچ عنوان روی برنچ های ریلیز قرار نگیرند۹. شاید یک دولوپر کارش نیازمند و وابسته به کار دولوپر دیگیری باشدروند (GitFlow) پیشنهادی مابرنچ های پیشنهادی ما : برنچ Develop : این برنچ حاوی کد پایدار است. این برنچ تمام فیچر های کامل شده و پایدار را شامل میشود. این فیچر ها تست شدند، تمام مراحلشان تمام شده و اماده ریلیز شدن هستند. این برنچ فقط توسط مدیر تیم یا ارشد هایی که وظیفه بررسی کد را دارند مدیریت میشود و دولوپر ها تنها از طریق Pull-Request، میتوانند درخواست خود را برای ثبت کدهایشان روی برنچ Develop بدهند و بعد از اینکه ارشد ها، کدها را بررسی کردند و از همه نظر سالم بود، این درخواست را قبول میکنند و آن کدها روی برنچ Develop با Merge (یا Rebase) قرار می گیرند.برنچ های Feature : این برنچ ها از Develop ساخته می شوند. وقتی قرار است یک فیچر به اپلیکیشن اضافه شود، یک برنچ از Develop گرفته میشود و فیچر جدید روی آن توسعه داده می شود. برای قاعده مند بودند اسامی برنچ ها، هر فیچر جدید با کلمه features به همراه یک / شروع می شوند مثلfeatures/login-pagefeatures/profile-elastic-headerمعمولا هر دولوپر روی یک برنچ فیچر توسعه میدهد. ولی زمانی پیش میاد که چند دولوپر میخوان روی یک برنچ فیچر کار کنن. مثلا فیچر خیلی بزرگ هستش. در این مورد، ما تنها یک برنچ روی ریموت و آنلاین و ریپازیتوری داریم ولی دولوپر ها هرکدام، این برنچ را روی سیستم خودشون کلون میکنند و روی سیستم لوکال خودشون برنچ خودشون رو درست میکنند. در این حالت پیشنهاد می شود تنها در دو حالت روی برنچ فیچر اصلی که روی ریموت قرار داره، push زده بشه، زمانیکه اون فیچر توسط دولوپر تموم شده و یونیت تست ها انجام شدهزمانیکه کار یکی از دولوپر ها وابسته به کار دیگری است، در این حالت دولوپر اول کار را انجام داده و روی برنچ ریموت پوش میکند و دولوپر دوم میتواند کار را شروع کند. باید درنظر داشت که اگر می شود اتومیک این وابستگی حل شه، این کارو باید بکنیم یعنی سریعا اون وابستگی رو قبل کارهای دیگه حل کنیم و پوش روی ریموت بزنیم و ادامه کار را روی لوکال خودمون انجام بدیمفیچر ها میتونند همون موقع که تموم میشند روی Develop قرار بگیرند یا اینکه منتظر باشن تا زمانیکه ریلیز بشند. نحوه برخورد ما با این مسئله اینگونه است : فیچر های تمام شده که همان در ریلیز بعدی باید قرار بگیرند. در این حالت بعد از تست pull-request به Develop داده می شود و بعد از ریویو توسط ارشد یا مدیر، روی Develop قرار میگیرد و اماده ریلیز است. بعد از مرج شدن با Develop، برنچ این فیچر حذف می شود.فیچرهای حجیمی (به سایز اپ اضافه میکنند، assets دارند، دیپندنسی دارند و ... ) که زمان مشخصی برای ریلیز ندارند و باید صبر کنند اصطلاحا Long Live Branches، در این حالت برنچ فیچر تا زمانیکه با Develop مرج نشود باقی می ماند ولی این فیچر می تواند از یک روز تا چند ماه شایدم چند سال باقی بماند، در این حالت باید حواسمان به این موضوع باشد که هر چند وقت یکبار این برنچ را از Develop pull کنیم تا تغییرات Develop را روی این برنچ داشته باشیم و آن را آپدیت کنیم و اگر کانفلیکتی برخوردیم برطرف کنیم. وقتی میگیم چند وقت یکبار به این دلیل است که اگر بعد مدت طولانی این برنچ را بخواهیم روی Develop مرج کنیم اول باید حتما از برنچ Develop یک pull و اپدیت کنیم برنچ را اینجور تغییرات و احتمالا کانفلیکت ها خیلی خیلی زیاد است و ممکن است اصلا کلا روند آن فیچر تغییر کند. در نتیجه pull های نزدیک و متوالی میتواند برنچمان را تا زمان ریلیز شدن آپدیت نگه دارد.فیچر های سبک، در این سبک از فیچر ها که شامل تنها کد هستند و از جاهای محدودی در اپلیکیشن به آن ها دسترسی داریم، از  Feature Flag استفاده می کنیم. این مفهوم خیلی ساده است، ما در یک فایل، دیتابیس (اگر تعداد زیاد باشد) یا حتی یک دیکشنری استاتیک درون برنامه، فیچیر های فعال و غیر فعال را مشخص میکنیم. مثلا صفحه استعلام اسناد تجاری آماده و تست شده و فقط از طریق منو، قابل دسترسی است. ما اصطلاحا یک Toggle Point در منو درست میکنیم و این فیچر را در آنجا قرار میدهیم و آن را غیرفعال میکنیم یعنی در منو نمایش داده نمی شود و در نهایت بعد از تست نهایی pull-request را به برنچ Develop میفرستیم و این فیچر روی برنچ Develop ما قرار میگیرد و برنچ این فیچر پاک می شود. تا زمانیکه  فرصت به ریلیز این فیچر برسد، آن غیر فعال است و وقتی زمان ریلیز این فیچر می رسد به راحتی آن را در هماه فایل یا دیتابیس یا دیکشنری که از آن قرار دارد، فعال میکنیم و از این به بعد در اپلیکیشن نمایش داده می شود.برنچ ّIssue (یکی از برنچهایی که ما به فلو استاندارد اضافه کردیم): این برنچ یک برنچ همیشگی است. ما آن را برای رفع مشکل تغییرات یا باگ های کوچک می سازیم و هیچوقت پاک نمی شود. این برنچ هر روز صبح از برنچ Develop یکبار pull می شود و تغییراتی مثل تغییر رنگ یک لیبل، تغییر یک نوشته، بزرگ کوچک کردن یک دکمه از آن استفاده میکنیم. این برنچ را ساختیم چون به صورت مستقیم روی برنچ Develop نمی توانیم push کنیم و از طرفی ساختن یک برنچ برای هر باگ یا تغییر کوچکی مثل مثال هایی گفته شد، کار زمان بر و خسته کننده ای هستش. ما اخر هر روز این تغییرات کوچیک انجام شده رو pull-request برای برنچ Develop میفرستیم و مرج میکنیم. نکته ای که وجود داره اینه که هر روز صبح pull و آخر روز کاری اگر تغییری انجام شده با برنچ Develop مرج کنیم (pull-request) و همچنین هر زمانی  که خواستیم ریلیز بدیم، اونو اول با برنچ Develop مرج (pull-request) کنیم.برنچ های Bug : این برنچ ها برای رفع باگ ها از برنچ Develop گرفته میشن و بعد از تصحیح و رفع اون باگ، برای برنچ Develop درخواست فرستاده میشه (pull-request) و بعد از تایید و مرج شدن با برنچ Develop، این برنچ ها پاک میشند.(البته ممکن است برای یک برنچی باشند که هنوز روی برنچ Develop قرار نگرفته که در این حالت از خود اون برنچ ساخته میشه و بعد اتمام روش push میشه) در قاعده نامگذاری به این شکل کار میکنیم. کلمه bugs به همراه / و نام اون برنچ و اگر در جیرا یا جایی دیگر ریپورت شده شماره اون ریپورت به همراه #bugs/login-message-not-show#44bugs/api-repsonde-404-not-handled#4337برنچ های Release :  این برنچ ها تنها قبل از ریلیز شدن ساخته میشن. قبل از هر ریلیز ما از برنچ Develop یک برنچ می سازیم و اونو میدیم به تیم تست، این تست شامل کل اپلیکیشن است، فیچر ها قبلا دونه دونه و جدا جدا در زمان توسعه تست شدند و روی برنچ Develop قرار گرفتند، در نتیجه برنچ Develop ما باید استیبل باشد ولی قبل از ریلیز نهایی، ما برنچی می سازیم و آن را میدهیم دست تیم تست تا یکی دو روز آن را تست کنند و یکپارچگی سیستم را بررسی کنند، چون ممکن است کدها هیچ ایرادی نداشته باشند ولی در جایی چیزی را پاک کردیم که چند ماه قبل در جایی دیگر از آن استفاده کردیم، این ها را یکبار توسط یونیت تست و بار دیگر توسط تیم تست به صورت دستی تست میکنیم. شاید بگیم که برنچ Release نیاز نیست و می شود مستقیم از برنچ Develop این کار تست را انجام داد، ولی بعضی وقتها تست یکی دو روز یا سه روز انجام می شود و تیم توسعه در حال توسعه سرویس های دیگر است. در این مدت تست، میتواند برنچ Develop تغییر کند و فیچر جدیدی اضافه شود ولی نیاز نباشد در ریلیز قرار بگیرد. در نتیجه ما از برنچ Release استفاده میکنیم تا بتوانیم این مورد را برطرف کنیم. وقتی تست تمام شد و تیم تست تایید کرد،  پابلیش می شود و خروجی میگیریم و این برنچ، روی برنچ Master  مرج می شود (توسط مدیر تیم یا ارشد (pull-request))و در نهایت حذف می شود. برای نام گذاری این برنچ ها از این روش استفاده میکنیم. کلمه برنچ Releases به همراه / و سپس ورژن این ریلیز مثلreleases/v1.1برنچ Master : این برنچ شامل کد نهایی که پابلیش شده و دست مردم است، می باشد. این برنچ شامل تاریخچه ریلیز های ما است. این برنچ همیشه در کنار برنچ Develop هست و پاک نمی شود. بعد از اینکه تیم تست تایید نهایی را روی برنچ Release دادند ما آن برنچ را روی Master مرج میکنم. ریلیز میدهیم و این ریلیز را تگ میکنیم و برنچ Release را پاک میکنیم. با تگ کردن، ما تاریخچه ریلیز هامون رو نگه میداریم و هر جا نیاز بود می توانیم به آن ها مراجعه کنیم. این برنچ پایه و اساس درخت گیت ما هستش و هرکسی نیاز به خروجی و ریلیز گرفتن داشت باید به این برنچ مراجعه کند و از این برنچ استفاده کند به این دلیل که این برنچ شامل پایدارترین حالت اپلیکیشن است و این برنچ چیزی است که در حال حاضر دست مردم قرار دارد. برنچ های Hotfix : ما از این برنچ ها برای رفع سریع مشکلات موجود و دیده نشده درون ورژنی که ریلیز شده استفاده میکنیم. این برنچ ها از روی برنچ Master ساخته می شوند و باگ فیکس شده و به سرعت روی برنچ Master مرج می شود (pull-request) و همان برنچ ریلیز دوباره برای پابلیش شدن می رود. دقت کنیم وقتی hotfix انجام شد، یک درخواست روی برنچ Master ارسال میکند و یک درخواست روی برنچ Develop، اینجوری برنچ برنچ Develop هم اون تغییرات رو میگیره و اپدیت میشه و این باگ هم روی برنچ Develop رفع شده و هم روی برنچ Master. بعد برنچ Master با ورژن جدید تگ میشه و وقتی این باگ روی برنچ Develop مرج شد، این برنچ hotfix پاک می شود. برای نام گذاری از hotfixes به همراه / استفاده میکنیم. مثلhotfixes/removing-currency-rate چه جایگزین هایی هست؟مواردی که گفته شد، شاید برای بعضی شرکت ها زیاد باشه، برای ما تئوریکال خیلی خوب بود. ولی وقتی در عمل وارد میشی شاید همه چیز اینقدر مرتب و رویایی نباشه، ما متوجه شدیم که نمیتونیم همیشه تمیز و با ادب جلو بریم، اینجا هستش که دستورات Merge و Rebase به کمکمون میاد و همچنین متوجه شدیم که این Flow که بش فکر میکنیم شاید پایبند بودن بش سخت باشه. مهمترین نکته برای استفاده از این فلو، اینه که ما دو برنچ اصلی و مهم داریم که روی یکی فیچرهای تمام شده رو نگه میداریم و روی دیگیری، نسخه ای که دست مردم است در این حالت همیشه استیبل ترین حالت ما می شود نسخه ای که دست مردم است و همیشه از این برنچ که مستر است می توانیم خروجی بگیریم و نسخه ای که برای توسعه استفاده میکنیم برنچ Develop است.قوانینی که رعایت میکنیمبرنچ Master همیشه و در همه حال اماده خروجی گرفتن است و حاوی پایدارترین حالت کد ها هست.افرادی که دسترسی ندارند به هیچ عنوان نمیتوانند روی برنچ Master پوش کنن و تنها راه ارتباطی اونا با برنچ Master از طریق pull-request است.تمام برنچ های فیچرهای جدید و باگ فیکس ها از برنچ Develop ساخته می شود.فیچر ها قبل از پوش روی برنچ Develop، کاملا تست می شوند و این تست تنها و تنها شامل همان فیچر است . پس از اتمام تست و ادغام با برنچ Develop برنچ این فیچر پاک می شوداگر فیچری قرار نیست فعلا در ریلیز قرار بگیرد، تا آن زمان با  برنچ Develop ادغام نمی شود و برنچش باز می مانداگر فیچری با برنچ Develop ادغام شد یعنی آن فیجر تست شده و آماده ریلیز است. برنچ Issue فقط و فقط برای رفع مشکلات ساده مثل تغییر یک لیبل، رنگ یک دکمه و همچنین مواردی استفاده می شود. تغییرات باید اینقدر کوچک باشند که با چشم راحت بررسی شوند.برنچ Issue قبل هر تغییری از برنچ Develop اپدیت می شود تا اگر دیگران روش کار کردند اپدیت شویم و قبل از ریلیز یا آخر هر روز با برنچ Develop ادغام می شود.برای خروجی گرفتن، یک برنچ Release از برنچ Develop درست میکنیم و تمام تست های مربوطه را روی آن انجام میدهیم و وقتی تمام شد، خروجی میگیریم و این برنچ Release را به مستر میدهیم و تگ گذاری میکنیمبرنچ های Release بعد از ادغام با مستر پاک می شوند و روی مستر تگ با شماره آن ریلیز قرار میگیرد.باگ هایی که در خروجی پیدا می شوند و سریعا باید رفع گردند، را برنچ HotFix میگیم و از روی برنچ مستر یک برنچ HotFix درست می کنیم و تغییرات را روی آن میدهیم و با مستر ادغام میکنیم دوباره خروجی میگیرم و تگ میکنیم و این برنچ را با برنچ Develop هم ادغام میکنیم که تغییرات روی آن هم اعمال شود.هات فیکس ها برای این وجود دارند که ما نمیخواهیم فیچرهای جدیدی که روی برنچ Develop آماده شده اند روی خروجی بیایند در نتیجه ما از خود برنچ Master برنچ می سازیم و فیکس میکنیم.روی مستری هیچ چیزی پوش نمی شود مگر اینکه ریلیز شده باشداگر قرار است چندتا فیچر با هم برای تست داده شوند ولی در خروجی نمی آیند میتوانیم همه برنچ ها را در یک برنچ دیگر به نام برنچ Epic ادغام کنیم و خروجی بگیریماستفاده از کد گذاری ها و نامگذاری ها برای مدیریت بهتر و سریعتر استفاده از کاراکتر های خاص در کامیت ها برای اینکه به سرعت بفهمیم که این کامیت مربوط به چه چیزی بوده و چه کاری روش انجام شده. این ها کاملا قراردادی بوده و هرکسی برای خودش میتونه درست کنه. لیست کامل کاراکتر ها و اموجی ها رو میتونین اینجا ببینین?tada: این فیچر تمام شده است ? :construction: این فیچر هنوز تمام نشده و پوش در آخر روز ? :lipstick: ظاهر کاربری این فیچر تکمیل شده است? :pencil: کدهای این فیچر تکمیل شده است? :bug: باگ برطرف شده است? :wrench: نیاز به ریویو و ریفکتور دارد✅ :white_check_mark: تست برای این فیچر تکمیل شد یا استفاده از کلمات ساده مثلdone: این فیچر تمام شده است  construction: این فیچر هنوز تمام نشده و پوش در آخر روز  ui: ظاهر کاربری این فیچر تکمیل شده است code: کدهای این فیچر تکمیل شده است bug: باگ برطرف شده است review: نیاز به ریویو و ریفکتور دارد test: تست برای این فیچر تکمیل شداسم گذاری برنچ ها به این شکل انجام می شود releases/{version}-{buildNumber(optional)} --&gt; releases/v2.4.23-1023

hotfixes/{hotfix-title} --&gt; hotfixes/removing-currency-rate   

bugs/{bug-title} --&gt; bugs/api-repsonde-404-not-handled#4337

features/{sub-feature(optional)}/{feature-title} --&gt; features/login-page/register

features/{feature-title} --&gt; features/firebase-pageOur Gitflow</description>
                <category>farshadjahanmanesh</category>
                <author>farshadjahanmanesh</author>
                <pubDate>Mon, 31 Dec 2018 16:51:20 +0330</pubDate>
            </item>
            </channel>
</rss>