kenegozi.com

<form id='kenegozi' action='post'></form>

   
2008 Jul 21

Patch management approaches using decent CSM

tagged as: tools | Source Control

Following Ayende's post on Patch management approaches using centralized SCM, here are how I would have dealt with the 4 issues that he brings up, using a Decentralised SCM.

 

I use git, so I'll use git terms here. I guess it's quite similar for other DSCM systems.

 

Note that I haven't used patches on git development as until now all of my git work was on repositories I had write access to, However the principals are the same (i.e. - all of the tree is local to my machine, thus I can reach any point in the history locally).

 

First I'll clone the hosted repository to my local machine.

  • #1
    I'd have created a separate local feature branch for each feature, so separating the patches is easy
  • #2
    again, I can do this in two separate local branches, so I do not need to "revert and apply" when I move between the two. I also get to have a complete SCM experience, not only a single patch/step per feature.
    I can also have a third branch, combining the work of the two feature branches, for my own use
  • #3
    the second feature's branch would be based on the first one. should the first need some rework that is important to the second, it'd be easy to apply changes on the first, then rebase the second ontop of the updated first
  • #4
    just two commits on the same branch.

So, using a DSCM, I can work locally with the benefits of a SCM, have as many branches/features as I want. the whole tree is stored locally, and its blazing fast to switch branches, so I can easily work on every aspect I want, and easily create a patch from every node in the history tree, to send to the project owners.

2008 Jul 19

MonoRail sample gone AspView

tagged as: castle | monorail | aspview

Some more AspView love:

This dude, Morten Lyhr (great blog - go on and subscribe), has taken the sample MonoRail Getting Started project and AspView-ed it.

 

Take a look.

2008 Jul 16

I didn't brake the build

tagged as: castle | monorail | aspview

After making it build locally and reaching the conclusion that AspView builds correctly as part of the main Castle build , I've commited the changes to the repository, and the build server appear to agree with me:

Build_Succeded_on_the_build_server

2008 Jul 16

Build Succeeded - A happy red screen

tagged as: castle | monorail | aspview

can you guess why this makes me happy?

Build_Succeded

This is the output of building Castle's trunk, both for .NET 3.5 and .NET 2.0, after inserting AspView into the core project. Took me a while as I had to:

  1. Change the Xunit tests into NUnit - to match the runner
    wasn't too complicated, though I has to manually add [SetUp] and [TestFixture] everywhere, as they're not needed in Xunit
  2. Setting the correct Castle license snippet on every file
  3. Making the build pass and run all the tests correctly.
    now that was a royal PITA, as part of the tests include compiling view templates from source files, and copying files to the build folder using NANT is not simple, as the <copy> task flattens the source directory structure. For now I settled on specifying each views folder in the build file but Im looking at improving that bit.

So, soon enough (hopefully by the end of this day) you'd be able to see AspView on the build server.

 

Thx again for all of the users and patch-contributors for your faith in this library.

2008 Jul 16

Another one bites the dust ...

Not tagged yet

Following many other good fellas, (like Scott Hanselman, Damien Guard, Phil Haack, Justin Angel and many more), one more has joined Microsoft.

 

Hamilton Verissimo, the founder of Castle Project, and an inspiration to myself and many others, would most probably serve as another great power in the DevDiv, which appear to be an awesome place to work at, more and more every day.

 

Way to go Hammett.

2008 Jul 16

Name That Code quiz

tagged as: miscellanea

A cute programming languages quiz.

It'd show you 12 snippets of code, and you'd have to guess the programming language the code is written in.

 

If you have only started coding in the late 90's then you're in trouble.

heck, even if you have started on late 80's. I mean, really.

 

As I've been exposed to programming from a very early age, on the first half of the 80's, and my father being and old time punching-cards hacker, and I also tend to reach for the new stuff these days, I managed to score a nice rounded 12/12 100 points.

 

Can you?

 

Name That Code
OnePlusYou Quizzes and Widgets

2008 Jul 14

Alt.NET Israel conf - registration is open

tagged as: alt-net-israel

It's on "First in first served" basis, and there is a limited capacity, so go ahead and register at the conference page:

 

http://altdotnet.org/events/3

 

You'd need an openid identity in order to register. If you don't have one, that's be a great opportunity to get yourself one. it's free, and it's gaining more and more popularity as a SSO mechanism for the web. I'm using myopenid.com - signing up was simple, easy and fast.

 

IMPORTANT:

Please do not register, just because of the free admission if you don't think that you'd come. Otherwise you'd be taking a place of someone else's.

If you do register and later on find out that you won't be able to take part, please contact us organisers so we'd be able to add people from the waiting list.

 

if you blog - go ahead and spread the word.

if you can - tag it with "alt-net-israel" and/or "altnetconf" so it would propagate to the aggregators.

 

cya there

2008 Jul 13

Announcing ALT.NET Israel - the community driven (un)conference

tagged as: alt-net-israel

I'm really pleased to announce that there is going to be an Alt.Net conference in Israel, namely Alt.Net.Israel.

 

So what is Alt.Net?

If you haven't heard of Alt.Net yet, read David Laribee's post to better understand the term - What's ALT.NET

 

Details:

The conference will be held on Thursday 7th and Friday 8st August 2008, at the SQLink offices in Ramat Gan, and is being organised by Roy Osherove, Oren Eini (a.k.a Ayende), and myself.

 

Thursday 7th, at 18:30-20:30: planning meeting, following a walk to a nearby pub or coffee shop to socialise.

 

Friday 8th, at 09:30-16:30: sessions.

 

We have chosen a summer Friday and a super accessible location on purpose, to give the religious people a chance to attend and still make it on time home for Sabbath.

 

Agenda:

That is really up to the people who attend.  We will be following an open spaces format, similar to the other alt.net conferences in the UK, USA and Canada, where the agenda is decided by the conference participants.  Anyone can lead sessions on particular topics of interest, participate as an attendee or just hang around and chat with interesting people.

 

Please note that registration is not open yet!  I will blog more when we have information on this, hopefully it will open shortly. I can say that the conference will be free of charge.

 

If you have any questions, please feel free to contact us. I'm really looking forward to this, should be a great event!

 

 

A big thank you to our sponsors:

 

See you there :)

 

P.S, also a big thankyou to Ben Hall, of the alt.net UK organisers, which is partly responsible for my enthusiasm for alt.net conferences, and I've also used his previous announcement as a template for this one ...

2008 Jul 12

int.Parse != parseInt

tagged as: client-side | Javascript

Serving as a mental note, and as a service to dear readers who hadn't been bitten by this yet.

 

javascript's parseInt method is not the same as .NET's int.Parse.

 

there's this 'radix' argument which is meant to tell the parseInt method whether we want to treat the string we parse as binary, octal, decimal, hexadecimal or whatever.

Now the naive programmer (a.k.a. myself) would think that the default is always base 10, so parseInt(x) === parseInt(x, 10) for every x.

 

Apparently parseInt tries to outsmart us, and it's actually guessing the radix if not set. so if x begins with 0x, it would guess hexadecimal, and if x begins with 0 it would guess it's octal.

so, parseInt('010') === parseInt('010', 8) === 8

ok, I can live with that maybe.

however it would also 'guess' that 09 is octal (even though 9 is not an octal digit !) thus parseInt('09') === 0

 

I found this by chance, when a Date.parse method I have was parsing "09/07/2008" into a date-info object with day==0, causing it to fall back into today's date

 

So, the lessons we've learned today:

  1. javascript is not c#
  2. always set the radix when using parseInt - parseInt(x, 10)
  3. don't let your cat spill a glass of soda on your desk as it would ruin your earphones, and unless the laptop was on an elevated stand it would have ruin it also
2008 Jul 12

Building Castle on Vista

tagged as: castle

So after moving to Vista last week, I've tried a full castle build with tests.

 

Things I had to take care for it to run properly (from easy to not-as):

  1. Make sure Nant is in the path
  2. Make sure that NUnit 2.2.x is in the path
    explanation: for some reason, the remoting tests fail when being run from NUnit 2.4.x   As I'd rather not to gac any specific NUnit version, I have on my C:\Program Files two separate directories, one called "NUnit 2.2.8" and one called "NUnit 2.4.7", and the shortcut I use for firing a Command Prompt for Castle is making sure that NUnit 2.2.8 is in the path.
  3. Setup the test databases for DB related integration tests (as explained in "How To Build.txt")
  4. Make sure that you use an elevated command prompt - the shortcut I've mentioned on 2. is set as "Run As Administrator"
  5. To make the WcfIntegration facility tests run correctly, you need to run this thing once:
    sc.exe config NetTcpPortSharing start= demand
  6. some config files are missing from the build folder (Castle\build). until we fix it in the nant script, you have to manually run
    copy ..\Facilities\Wcf\Castle.Facilities.WcfIntegration.Tests\Configure*.xml ..\Build

 

Now that I have a way to run the build and make sure all tests pass, I can start working on my next Castle assignment - bringing AspView into the core project, but that's a whole other post so keep your RSS reader open ...

2008 Jul 3

Live, from Vista

tagged as: visual studio | miscellanea

My poor old laptop has had a lot of problems lately, priming at ignoring any network connection yesterday and having many problems with svn and git sessions when the network was on, so I decided to re-install.

 

'twas 1am, so I thought 'what the heck - let's try this vista thing at last'.

 

It was surprisingly a smooth experience. The initial setup identified almost all of the drivers, but the sound-card and the SD card reader. However, the auto updates (which took over an hour cuz there was apparently a lot to update) took care of the sound, and I got the SD driver from Texas Instrument's site.

 

What I had to install to make the machine workable for day-to-day work:

  • Antivirus (AVG)
  • VS2008
  • R#4
  • msysgit
  • Windows Live (Messenger + Mail + Writer)
  • TortoiseSVN
  • FF3 + Firebug + IEtab + FireFtp + Google Toolbar
  • Notepad2 (and making it a notepad replacement)

still missing (no time) but essential:

  • SnagIt
  • Camtasia Studio
  • Launchy

 

btw, since I've installed VS2008 without going 2005 first and without the full SDKs, I ran into a problem with NAnt 0.86b1 - complaining about missing .NET 2.0 stuff.  It appear to be a known bug in NAnt, that has been fixed back on late 2007, so I've just switched to a nightly build of 0.86b2 and the problem did go away.  I need to make sure that it won't affect my Castle build.

 

Didn't have much to say here. I consider it a test post (see if Writer will work from Vista) but it beats the crap out of "TEST POST PLEASE IGNORE" ...

2008 Jun 28

FTP Upload in .NET - You ain't need no libraries

tagged as: c#

Lately I've been asked about doing FTP related stuff in .NET .

There appear to be many "Ftp Clients" out there on CodeProject and other sites.

I really don't get 'em.

They are simple a leaky abstraction on top of straightforward BCL classes.

 

So what my solution is?

   1:  public void Upload(string server, int port, string targetFolder, string fileName, string username, string password, bool isActive)
2: {
3: var url = string.Format(
4: "ftp://{0}:{1}{2}/{3}", server, port, targetFolder, fileName)
5: using (var ftp = (FtpWebRequest)WebRequest.Create(url))
6: {
7: ftp.Credentials = new NetworkCredential(username, password);
8: ftp.KeepAlive = false;
9: ftp.UseBinary = true;
10: ftp.Method = WebRequestMethods.Ftp.UploadFile;
11: if (isActive)
12: ftp.UsePassive = false;
13:  
14: using (var writer = new BinaryWriter(ftp.GetRequestStream()))
15: writer.Write(File.ReadAllBytes(fileName));
16: }
17: }

 

This basic notepad code covers most of the functionality in FtpWebRequest. You can easily set Binary/ASCII, Active/Passive, Credentials and whatnot.

 

Alternatively, in some cases you can just spawn a ftp.exe process with a simple ftp script. Anyway you can rid yourself from unneeded leaky abstractions.

2008 Jun 28

FileBinderAttribute to ease FileUpload in MonoRail

tagged as: asp.net 2.0 | c# | castle | monorail

Following Scott Hanselman's post on FileUpload in ASP.NET MVC, I'll add here a few bits on doing that in MonoRail.

 

First, as MonoRail is an extension on top of plain ol' ASP.NET, just as ASP.NET MVC is, you can do the exact same thing - i.e iterate over Request.Files, and use a mocked Files collection for test or something.

 

But as the action parameters binder is very smart, and easily extensible, it's even nicer to just bind the posted data to a HttpPostedFile, using a FileBinder:

 

   1:  [AttributeUsage(AttributeTargets.Parameter, AllowMultiple = false, Inherited = false)]
2: public class FileBinderAttribute: Attribute, IParameterBinder
3: {
4: public int CalculateParamPoints(IEngineContext context, IController controller, IControllerContext controllerContext, ParameterInfo parameterInfo)
5: {
6: var key = parameterInfo.Name;
7: return context.Request.Files[key] != null ? 10 : 0;
8: }
9:  
10: public object Bind(IEngineContext context, IController controller, IControllerContext controllerContext, ParameterInfo parameterInfo)
11: {
12: var key = parameterInfo.Name;
13: return context.Request.Files[key] as HttpPostedFile;
14: }
15: }

 

So a custom binder is an attribute, that implements IParameterBinder, a two methods interface:

  1. CalculateParamPoints() - is for helping the framework correctly guess the best candidate of the action overloads. If the file exists in the request then it makes an action with a HttpPostedFile parameter with the name of the file upload name, a better candidate than an overload with a String parameter with the same name.
  2. Bind() - well, kinda' self explanatory.

 

so now you're action can look like this:

   1:  public void Save([FileBinder] HttpPostedFile myfile)
2: {
3: if (myFile != null)
4: {
5: // do stuff with the file
6: }
7: }

 

Cool? well actually what really is cool is that binding to HttpPostedFile is baked into MonoRail to begin with - so you don't even need this FileBinderAttribute at all ! you can simply

   1:  public void Save(HttpPostedFile myfile)
2: {
3: if (myFile != null)
4: {
5: // do stuff with the file
6: }
7: }

 

So why did I show you that?

Testablility.

Since HttpPostedFile is not easily mockable* (cuz it's bloody sealed and not new-able), you should do what you always do when in need to bypass one of these un-testable hard-to-test* sealed classes: Adapter pattern. Introduce IHttpPostedFile, and supply your own HttpPostedFile encapsulating the built in one.

 

so:

1: [AttributeUsage(AttributeTargets.Parameter, AllowMultiple = false, Inherited = false)]
2: public class FileBinderAttribute: Attribute, IParameterBinder
3: {
4: public int CalculateParamPoints(IEngineContext context, IController controller, IControllerContext controllerContext, ParameterInfo parameterInfo)
5: {
6: var key = parameterInfo.Name;
7: return context.Request.Files[key] != null ? 10 : 0;
8: }
9:  
10: public object Bind(IEngineContext context, IController controller, IControllerContext controllerContext, ParameterInfo parameterInfo)
11: {
12: var key = parameterInfo.Name;

13: var file = context.Request.Files[key] as HttpPostedFile;
14: return file == null ? null : HttpPostedFileAdapter(file);
15: }
16: }

 

and

   1:  public void Save([FileBinder] IHttpPostedFile myfile)
2: {
3: if (myFile != null)
4: {
5: // do stuff with the file
6: }
7: }

 

 

 

 

 

 

* Yes Roy, I know you can throw some TypeMock magic at it

2008 Jun 26

Can you spot the bug?

tagged as: c#

 

DISCLAIMER:

If you are a potential client of mine, or rather a current one, please stop reading NOW, as it's one of these embarrassing "I am sometimes too stupid" posts.

 

 

 

Oh my.

 

That's how my 3am code can look like:

 

   1:  var page = filter.Page.GetValueOrDefault(1);
2: var pageSize = filter.PageSize.GetValueOrDefault(30);
3: var firstResult = (page - 1) + pageSize;

 

It's for NHibernate style paging (i.e. firstResult is for a 0 based index)

 

Spotted (thanks to DbAwareIntegrationTests) and fixed at 6pm

2008 Jun 23

Fabio and Ayende On Caching

tagged as: architecture | nhibernate

A quick ripoff from NHibernate's users group:

 

Fabio Maulo:

The base concepts to understand are (my opinion):
- *The Cache is not the panacea of performance.*
- Don't use the Cache like the base of your app; add the management of Cache at the end of your development process to increase the performance only where you really need do it.
- Implementing a method named GetAll is, in most cases, a bad idea; an acceptable mediation is PaginateAll(pageSize).
- InMemoryFilter can have less performance than filter trough RDBMS (especially when you intent to do it trough Cache with a large amount of entities).
- Take care on what happen to the memory usage of your app when you are using Cache.

 

Ayende:

The cache is not magic, and should not be treated in such a fashion. I refuse to use the 2nd level cache in my applications until I have a perf problem that can't be solved by creating smarter queries.
Think about the cache as band aid, and good design as avoiding the need for that.

 

And I say Hallelujahs

2008 Jun 22

Castle.Tools.* in Castle Contrib's repository has moved a bit

tagged as: css | html | tools | castle | SQL Server

The tools (various small helper libraries) are now under http://svn.castleproject.org:8080/svn/castlecontrib/Tools/

 

what's in there:

  1. Castle.Tools.StaticMapGenerator - That one creates a typed tree representing js/css/image files on the site's filesystem.
    more here:
    http://www.kenegozi.com/Blog/2008/01/17/staticmapgenerator-for-asp-dot-net-first-teaser.aspx
    Which reminds me that I need to add .swf files to the mix ...
  2. Castle.Tools.SQLQueryGenerator -  That one is for building plain old SQL strings in a typed and intellisense friendly way.
    more here:
    http://www.kenegozi.com/Blog/2008/01/27/already-added-stuff-to-sql-query-generator.aspx
  3. Castle.Tools.QuerySpecBuilder/ - The new kid in the block. That's a tool that is used to build specs programmatically, which would later be translated to a SQL string for your flavour of DAL. The generated SQL is mostly ANSI compliant, apart from the Paging syntax which is TSQL only currently, but at some point I'll add an extension point to allow other syntaxes.
    I also have an external thing to make it extremely useful with NHibernate's ISQLQuery.
    I'll blog about all that when I'll have a little time.
2008 Jun 22

Simple String Hashing in .NET

tagged as: c# | tools

I've been asked about it several times lately, so I'll just put here an oldie that I've been using for a few years now untouched:

 

   1:  // MIT license
2: // Copyright 2005-2008 Ken Egozi
3: //
4: // Permission is hereby granted, free of charge, to any person obtaining a copy
5: // of this software and associated documentation files (the "Software"), to deal
6: // in the Software without restriction, including without limitation the rights
7: // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8: // copies of the Software, and to permit persons to whom the Software is
9: // furnished to do so, subject to the following conditions:
10: //
11: // The above copyright notice and this permission notice shall be included in
12: // all copies or substantial portions of the Software.
13: //
14: // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15: // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16: // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17: // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18: // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19: // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20: // THE SOFTWARE.
21:  
22: using System;
23: using System.Collections.Generic;
24: using System.Text;
25: using System.Security.Cryptography;
26: using System.Collections;
27:  
28: namespace KenEgozi.CryptographicServices
29: {
30: public static class Hashing
31: {
32: private static Hashtable hashAlgorithms = Hashtable.Synchronized(new Hashtable());
33:
34: /// <summary>
35: /// Hashing a given string with SHA2.
36: /// </summary>
37: /// <param name="data">Data to hash</param>
38: /// <returns>Hashed data</returns>
39: public static string HashData(string data)
40: {
41: return HashData(data, HashType.SHA256);
42: }
43:
44: /// <summary>
45: /// Hashing a given string with any of the supported hash algorithms.
46: /// </summary>
47: /// <param name="data">Data to hash</param>
48: /// <param name="hashType">Hashing algorithm to use</param>
49: /// <returns>Hashed data</returns>
50: public static string HashData(string data, HashType hashType)
51: {
52: HashAlgorithm hash = GetHash(hashType);
53: byte[] bytes = (new UnicodeEncoding()).GetBytes(data);
54: byte[] hashed = hash.ComputeHash(bytes);
55: StringBuilder sb = new StringBuilder(64);
56: foreach (byte b in hashed)
57: sb.AppendFormat("{0:x2}", b);
58: return sb.ToString();
59: }
60:  
61: private static HashAlgorithm GetHash(HashType hashType)
62: {
63: if (!hashAlgorithms.ContainsKey(hashType))
64: hashAlgorithms.Add(hashType, CreateaHashAlgorithm(hashType));
65: return hashAlgorithms[hashType] as HashAlgorithm;
66: }
67:  
68: private static HashAlgorithm CreateaHashAlgorithm(HashType hashType)
69: {
70: switch (hashType)
71: {
72: case HashType.MD5:
73: return new MD5CryptoServiceProvider();
74: case HashType.SHA1:
75: return new SHA1Managed();
76: case HashType.SHA256:
77: return new SHA256Managed();
78: case HashType.SHA384:
79: return new SHA384Managed();
80: case HashType.SHA512:
81: return new SHA512Managed();
82: default:
83: throw new NotImplementedException();
84: }
85: }
86: }
87:  
88: public enum HashType
89: {
90: MD5,
91: SHA1,
92: SHA256,
93: SHA384,
94: SHA512
95: }
96: }

 

Not beautiful, however useful.

 

You can download this file from here (just remove the .txt - the server doesn't serve .cs files directly)

 

btw, the colouring of the source was made with the help of http://www.manoli.net/csharpformat/, even though I had to do some manual tweaking to make it work with this blog. If colours of reserved words, comments etc. do not appear, then please refresh your browser's cache to get the updated css

2008 Jun 20

The Fox Is Hungry

tagged as: tools

My impression on Firefox 3 by now:

  1. It looks nicer.
  2. It still eats up all of my poor machine's memory

The fox is hungry

2008 Jun 18

Download Firefox 3

tagged as: tools

 

I really don't need to add anything, right?

 

download-button-primary

 

 

 

Installed it myself today. Appear to be a bit faster, and to eat up less memory.

 

The Google Toolbar and FireFTP were updated automatically.

 

I needed to manually re-install FireBug and IE-Tab

 

btw, does anybody know where did the Back and Forward buttons has gone to? Im using the keyboard usually, but sometimes (especially during in-office-lunch-time) I need to click the Back thing with the mouse

 

UPDATE: it appear that as part of the upgrade, FF3 has inherited my customised toolbars and that's why it was looking weird.  So I right-clicked on the toolbar -> customise, the clicked "Restore Default Set". All the buttons came back, then I rearranged the toolbar to my liking.

2008 Jun 17

Naming Interfaces

tagged as: architecture | c#

An innocent question raised by Ayende has started an interesting debate on the comments.

 

In short (read it all there - don't be lazy)

Which interface name is better?

a. IRecognizeFilesThatNeedToBeIgnored

b. IIgnoreFilesSpecification

with a single method: ShouldBeIgnored(string file);

 

Some were in favour of a, some in favour of b.

The interesting thing is that many has offered a third option:

c. IFileFilter

 

Let's group these things:

  1. Options a. and b. => Narrow and very specific interfaces. You can guess exactly what a class implementing them can do.
  2. Option c. => a general-purpose interface. You'd know that a class that implement this type of interface is doing stuff with files, but it's kinda vague. Can it filter a file out of a list of files? can it filter the content of a file? can it do other kinds of filtering on some kinds of files?

Personally I couldn't care less which one of the first type will be used. I slightly in favour of b., as I think funny names are good. The compiler cares nothing about names, but the human mind would remember the purpose well, and a newcomer would pick it up quickly.

 

The second group (IFileFilter) is not good. It might get filled with a lot of methods that do file filtering.
and if it's not, I think it should reflect the intention of the implementing class.
Since multiple interfaces per class are allowed, it's ok to have specialised ones.

Subscribe

Statistics

283
440

Related Books

Related Jobs

Related Ads

search page | Blog's home | About me