از اونجایی که تولید محتوا کار مشکل و وقت گیری هست و سیاست این وبلاگ هم مخالفت با Copy&Paste هست، مطالب جدید و مفیدی که در کار و مطالعه روزانه بهشون بر می خورم رو در قسمت "پیوندهای روزانه" قرار میدم .
پس حتما بخش "پیوندهای روزانه" رو هم یه سر بزنید.
از اونجایی که تولید محتوا کار مشکل و وقت گیری هست و سیاست این وبلاگ هم مخالفت با Copy&Paste هست، مطالب جدید و مفیدی که در کار و مطالعه روزانه بهشون بر می خورم رو در قسمت "پیوندهای روزانه" قرار میدم .
پس حتما بخش "پیوندهای روزانه" رو هم یه سر بزنید.
بعد از مدت ها، تصمیم گرفتم ادامه نوشتن رو در دامنه mray.ir ادامه بدم.
ما در زمان جالبی زندگی می کنیم. به عنوان برنامه نویسانی که در سرار دنیا پخش هستیم، شما افراد توانمند زیادی رو در این حرفه پیدا می کنید. شما برای اینکه در بازار خریدار داشته باشید، نیاز دارید که به یادگیری خودتون ادامه بدهید. در غیر اینصورت تبدیل به فسیل خواهید شد، در شغل خود خواهید ماند تا اینکه روزی به درد نخور شوید یا با یک منبع ارزانتر جایگزین شوید.
حالا شما چکار می کنید؟ بعضی از کارفرمایان آنقدر سخاوتمند هستند که شرایط آموزش رو برای شما در جهت توسعه مهارت هاتون فراهم آورند، بعضی دیگر ممکنه نتوانند وقت یا پول کافی برای هر گونه آموزشی صرف کنند. برای اینکه راه امنی در پیش بگیرید، شما باید خودتون مسئولیت آموزش خودتون رو بر عهده بگیرید.
در اینجا لیستی از کارهایی که می تونید برای آموزش خودتون انجام بدید تهیه شده است :
خیلی خوبه که قابلیت نئو در فیلم ماتریکس رو داشته باشیم، و به سادگی اطلاعات مورد نیاز رو به مغزمون دانلود کنیم. اما نداریم! پس این یک تعهد زمانبر است. لازم نیست که هر روز بعد از بیدار شدن مشغول یادگیری شوید. یک زمان کم، مثلا هر هفته، از هیچی بهتر است. هر کسی باید یک زندگی غیر کاری داشته باشد.
تغییرات تکنولوژی خیلی سریع هستند، سعی کنید جا نمانید.
این مطلب برداشتی آزاد از قسمت Continuous Learning کتاب 97 things every programmer should know بود که خوندنش رو به همه دوستان و همکاران توصیه میکنم.
اگر با mvc کار کرده باشید حتما با ModelBinding آن آشنا هستید؛ DefaultModelBinder توکار آن که در اکثر مواقع، باری زیادی را از روی دوش برنامه نویسان بر می داردو کار را برای آنان راحتتر می کند، اما در بعضی مواقع این مدل بایندر پیش فرض ممکن است پاسخگوی نیاز ما در بایند کردن یک خصوصیت از یک مدل خاص نباشد، برای همین ما نیاز داریم که کمی اون رو سفارشی سازی کنیم.
برای این کار ما دو راه داریم:
1) یک مدل بایندر جدید با پیاده سازی از IModelBinder انجام دهیم. (در این حالت ما مجبوریم که مدل بایندر رو از اول جهت بایند کردن کلیه مقادیر شی مدل مون بازنویسی کنیم و در واقع امکان انتساب اون رو در سطح فقط یک خصوصیت نداریم.) (نحوه پیاده سازی قبلا در اینجا مطرح شده)
2) ModelBinder پیش فرض رو جهت پاسخگویی به نیازمون توسعه بدیم. (که در این مطلب قصد آموزشش رو داریم.)
فرض کنید که می خواهید از روی یک Enum در صفحه، یک DropDown معادل رو قرار بدید که به طور خودکار رشته انتخاب شده رو به یک خصوصیت مدل که از نوع بایت هست بایند بکند.
از طریق کد زیر یک DropDownFor برای Enum مورد نظر در مدل ایجاد کنیم:
@Html.DropDownListFor(model => model.AccountType, new SelectList(Enum.GetNames(typeof(Enums.AccountType))))
و کلاس Enum مورد نظر :
public enum AccountType : byte { مدیر = 0, کاربر_حقیقی = 1, کاربر_حقوقی = 2, }
حالا برای اینکه این مقدار انتخابی به صورت خودکار و از طریق امکان binding توکار خود MVC به خصوصیت AccountType مقدار دهی شود باید یک PropertyBindAttribute سفارشی بنویسیم، برای اینکار یک کلاس جدید با نام CustomBinding می سازیم و کدهای زیر رو به اون اضافه می کنیم :
namespace MvcApplication1.Models { [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public abstract class PropertyBindAttribute : Attribute { public abstract bool BindProperty(ControllerContext controllerContext, ModelBindingContext bindingContext, PropertyDescriptor propertyDescriptor); } public class ExtendedModelBinder : DefaultModelBinder { protected override void BindProperty(ControllerContext controllerContext, ModelBindingContext bindingContext, PropertyDescriptor propertyDescriptor) { if (propertyDescriptor.Attributes.OfType<PropertyBindAttribute>().Any()) { var modelBindAttr = propertyDescriptor.Attributes.OfType<PropertyBindAttribute>().FirstOrDefault(); if (modelBindAttr.BindProperty(controllerContext, bindingContext, propertyDescriptor)) return; } base.BindProperty(controllerContext, bindingContext, propertyDescriptor); } } }
در کد بالا ما تمام کلاس هایی رو که از PropertyBindAttribute مشتق شده باشند رو به DefaultModelBinder اضافه می کنیم. این کد فقط یک بار نوشته می شود و از این به بعد هر بایندر سفارشی که بسازیم به بایندر پیشفرض اضافه خواهد شد.
حالا از طریق کد های زیر، ما بایندرِ سفارشیِ خصوصیتِ خودمون رو به کلاس اضافه می کنیم :
public class AccountTypeBindAttribute : PropertyBindAttribute { public override bool BindProperty(ControllerContext controllerContext, ModelBindingContext bindingContext, PropertyDescriptor propertyDescriptor) { if (propertyDescriptor.PropertyType == typeof(byte)) { HttpRequestBase request = controllerContext.HttpContext.Request; byte accountType = (byte)Enum.Parse(typeof(Enums.Enums.AccountType), request.Form["AccountType"]); propertyDescriptor.SetValue(bindingContext.Model, accountType); return true; } return false; } }
در کد بالا ما مقدار رشته ای رو که از DropDown ارسال شده را به مقدار عددی متناظر تعریف شده آن در Enum تبدیل می کنیم و آن را به خصوصیت مورد نظر بازگشت می دهیم، از این به بعد فقط برای فیلدی که به شکل زیر نشانه گذاری شده باشد ما از این کلاس بایندر سفارشی استفاده می کنیم و مدل بایندر پیش فرض هم کار خود را خواهد کرد و بقیه مقادیر را بایند خواهد کرد » اطلاعات بیشتر
[AccountTypeBindAttribute] public byte AccountType { get; set; }
حالا باید این کلاس گسترش یافته ModelBinder رو به عنوان بایندر پیش فرض mvc قرار بدهیم، برای اینکار کد زیر را به فایل Global.asax.cs اضافه کنید:
ModelBinders.Binders.DefaultBinder = new ExtendedModelBinder();
کار ما دیگه تمومه و تا اینجای کار همه چی بدرستی کار می کنه ... تا اینکه شما تصمیم میگیری که از jquery.validate.unobtrusive برای اعتبار سنجی سمت کاربر استفاده کنید و می بینید به DropDown شما هم ایراد میگیره که حتما باید از نوع عددی باشد
The field نوع کاربر : must be a number.
برای حل این مشکل هم باید به صورت دستی validation سمت کاربر رو برای این DropDown غیرفعال کرد، که باید کدهای DropDownFor که در صفحه گذاشتید رو به شکل زیر تغییر بدید:
@Html.DropDownListFor(model => model.AccountType, new SelectList(Enum.GetNames(typeof(Enums.AccountType))),new Dictionary<string, object>() {{ "data-val", "false" }})
چند روز پیش در سایت سازمان نظام صنفی رایانه ای کشور به فایل های "تعریفه نرخ پایه خدمات فنی-تخصصی انفورماتیک در سال 92" و فایل Excel همراه اون که نحوه محاسبه دستمزد رو نوشته بود، برخوردم.
اما وقتی که به اعداد و ارقام نگاه می کنم به نظرم اینها از مریخ اومدن و با واقعیت بسیار فاصله دارند یا اینکه من اشتباه متوجه شدم.
به عنوان مثال : تعرفه خدمات نرم افزاری (نفر ساعت - ریال) به ازای تخصص برنامه نویس اینطور نوشته شده که
ضریب این تخصص 2.8 هست و رتبه شورا از 1 تا 7 می باشد و دستمزد ها به این شکل هستند:
1- 838,000
2- 745,000
3- 698,000
4- 670,000
5- 652,000
6- 638,000
7- 628,000
یعنی حداقل دستمزد یک برنامه نویس سطح 7 (پایین تر رتبه) ساعتی 62 هزار تومان هست ؟!
البته پارامترهای دیگری هم روی این ارقام تاثیر گذار هستند(مثل سابقه کار و یا منطقه جغرافیایی) اما فکر نکنم خیلی تفاوت ایجاد کنه!
حالا برام سوال پیش اومده که مبنای تعیین چنین رقم هایی از کجا اومده و آیا واقعا اینها در جایی اعمال هم میشه یا همینطور اَلَکی گذاشتند ؟!
آیا واقعا میشه این اعداد رو بیانگر ارزش واقعی این تخصص ها و کارها دونست و اینها رو در قیمت گذاری ها مداخله داد؟
ممنون میشم که دوستان نظرشون رو بگن چون تا اونجایی که من می دونم فکر نکنم هیچ جای ایران مبنای محاسبه دستمزها رو تعرفه ابلاغ شده از سوی شورای صنفی قرار بدهند.
در ضمن می تونید این دو فایل رو از سایت سازمان صنفی با آدرس زیر دانلود کنید.
http://www.irannsr.org/services/news...%B4%D8%B1.html
در این پست قصد دارم نحوه خواندن RSS ها یا به اصطلاح فارسی "خوراک" سایت ها رو آموزش بدم.
من اینکار رو در MVC انجام می دم اما با کمی تغییر می شه اونها رو در WebForm هم مورد استفاده قرار داد.
ابتدا یک کلاس جدید با نام مثلا BlogModel به قسمت Model خودتون اضافه کنید و بعد یک خصوصیت از نوع SyndicationFeed و با نام BlogFeed برای اون می سازیم.
public class BlogModel { public SyndicationFeed BlogFeed { get; set; } }
این کلاس در System.ServiceModel.Syndication قرار دارد و به ما امکان کار کردن با RSS و یا Atom رو در قالب یک سری خصوصیت ها می دهد.
در زیر برخی از خصوصیات آورده شده است که اینها در کلاس SyndicationItem موجود هستند:
فقط در استفاده از این خصوصیت های متوجه این نکته باشید که ممکن است هر کدام از این خصوصیت ها null باشند.
یک کنترل جدید با نام Home بسازید و ارجاع های System.ServiceModel.Syndication و همچنین System.Xml رو به اون اضافه کنید.
public ActionResult Index() { var model = new BlogModel(); const string strFeed = "http://webdeveloper.blog.ir/rss"; try { using (XmlReader reader = XmlReader.Create(strFeed)) { SyndicationFeed rssData = SyndicationFeed.Load(reader); model.BlogFeed = rssData; } } catch (System.Net.WebException) { return Content("Error in Reading RSS Feed"); } return View(model); }
حالا باید کدهای نمایش فید ها رو در قسمت View بنویسیم. که در اینجا من با یک حلقه اونها رو خوانده و 5 لینک جدیدتر رو نمایش میدم.
<div> @if (@Model.BlogFeed != null) { <ul> @foreach (SyndicationItem post in Model.BlogFeed.Items.ToList().Take(5)) { <li> <a href='@post.Links.First().Uri'> @post.Title.Text </a> </li> } </ul> } </div>
که در View خودتون شی مدل رو باید برابر Models.BlogModel قرار بدید و یک ارجاع هم به کلاس System.ServiceModel.Syndication جهت دسترسی به Intelisense ویژوال استودیو برای مشاهده خصوصیت های شی post بدهید.
اینجا و اینجا می تونید اطلاعات بیشتری رو درباره کلاس SyndicationFeed بدست بیارید و اینجا هم یک آموزش خوب دیگر در همین رابطه موجود است.
امروزه با توجه به وسعت تکنولوژی ها، زبان ها و پلتفرم های متفاوتی که موجود هستند، اینکه شما برای آینده کاری خود به عنوان توسعه دهنده نرم افزار، زمانتان را برای افزایش مهارتتان روی کدامیک سرمایه گذاری کنید کار بسیار مشکلی به نظر می رسد.
بعضی ها از من به عنوان توصیه می پرسند که چگونه یک برنامه نویس بهتری باشم؟
در اغلب موارد، سوال کسی که می پرسد بر این پایه است که آیا آنها وقت خود را بر روی یک تکنولوژی یا یک زبان برنامه نویسی خاص در مقابل دیگر زبان برنامه نویسی سرمایه گذاری کنند یا خیر؟
مدتی است که به این فکر می کنم که مهمترین و بی پایان ترین مهارتهایی که یک توسعه دهنده نرم افزار باید داشته باشد، تا به آنها بهترین فرصت های شغلی را بدهد و آنها را تاثیر گذار کند، چیست؟