答:
I have a solution but it will require a little work

pypreprocessor is a library that provides a pure c-style preprocessor for python that can also be use as a GPP (General Purpose Pre-Processor) for other types of source code.

Here's a basic example:

```<code>from pypreprocessor import pypreprocessor

pypreprocessor.input = 'input_file.c'
pypreprocessor.output = 'output_file.c'
pypreprocessor.removeMeta = True
pypreprocessor.parse()
</code>```

The preprocessor is extremely simple. It makes a pass through the source and conditionally comments out source based on what is defined.

Defines can be set either through #define statements in the source or by setting them in the pypreprocessor.defines list.

Setting the input/output parameters allow you to explicitly define which files are being opened/closed so a single preprocessor can be setup to batch process a large number of files if desired.

Setting the removeMeta parameter to True, the preprocessor should automatically extract any and all preprocessor statements leaving only the post-processed code.

Note: Usually this wouldn't need to be set explicitly because python removed commented code automatically during the compilation to bytecode.

I only see one edge case. Because you're looking to preprocess C source, you may want to set the processor defines explicitly (ie through pypreprocessor.defines) and tell it to ignore the #define statements in the source. That should keep it from accidentally removing any constants you may use in your project's source code. There currently is no parameter to set this functionality but it would be trivial to add.

Here's a trivial example:

```<code>from pypreprocessor import pypreprocessor

# run the script in 'production' mode
if 'commercial' in sys.argv:
    pypreprocessor.defines.append('commercial')

if 'open' in sys.argv:
    pypreprocessor.defines.append('open')

pypreprocessor.removeMeta = True
pypreprocessor.parse()
</code>```

Then the source:

```<code>#ifdef commercial
// Copyright 2012 (C) Acme Technology, All Rights Reserved.
// Very large, often varied and restrictive copyright license in English and French,
// sometimes also embedded in make files and shell scripts with varied
// comment styles.
#ifdef open
// GPL Copyright (C) Acme Technology Labs 2012, Some rights reserved.
// Acme appreciates your interest in its technology, please contact xyz@acme.com
// for technical support, and www.acme.com/emergingTech for updates and RSS feed.
#endif
</code>```

Note: Obviously, you'll need to sort out a way to set the input/output files but that shouldn't be too difficult.

Disclosure: I am the original author of pypreprocessor.

Aside: I originally wrote it as a solution to the dreaded python 2k/3x maintenance issue. My approach was, do 2 and 3 development in the same source files and just include/exclude the differences using preprocessor directives. Unfortunately, I discovered the hard way that it's impossible to write a true pure (ie doesn't require c) preprocessor in python because the lexer flags syntax errors in incompatible code before the preprocessor gets a chance to run. Either way, it's still useful under a wide range of circumstances including yours.

Body:
I have a solution but it will require a little work

pypreprocessor is a library that provides a pure c-style preprocessor for python that can also be use as a GPP (General Purpose Pre-Processor) for other types of source code.

Here's a basic example:

from pypreprocessor import pypreprocessor

pypreprocessor.input = 'input_file.c'
pypreprocessor.output = 'output_file.c'
pypreprocessor.removeMeta = True
pypreprocessor.parse()

The preprocessor is extremely simple. It makes a pass through the source and conditionally comments out source based on what is defined.

Defines can be set either through #define statements in the source or by setting them in the pypreprocessor.defines list.

Setting the input/output parameters allow you to explicitly define which files are being opened/closed so a single preprocessor can be setup to batch process a large number of files if desired.

Setting the removeMeta parameter to True, the preprocessor should automatically extract any and all preprocessor statements leaving only the post-processed code.

Note: Usually this wouldn't need to be set explicitly because python removed commented code automatically during the compilation to bytecode.

I only see one edge case. Because you're looking to preprocess C source, you may want to set the processor defines explicitly (ie through pypreprocessor.defines) and tell it to ignore the #define statements in the source. That should keep it from accidentally removing any constants you may use in your project's source code. There currently is no parameter to set this functionality but it would be trivial to add.

Here's a trivial example:

from pypreprocessor import pypreprocessor

# run the script in 'production' mode
if 'commercial' in sys.argv:
    pypreprocessor.defines.append('commercial')

if 'open' in sys.argv:
    pypreprocessor.defines.append('open')

pypreprocessor.removeMeta = True
pypreprocessor.parse()

Then the source:

#ifdef commercial
// Copyright 2012 (C) Acme Technology, All Rights Reserved.
// Very large, often varied and restrictive copyright license in English and French,
// sometimes also embedded in make files and shell scripts with varied
// comment styles.
#ifdef open
// GPL Copyright (C) Acme Technology Labs 2012, Some rights reserved.
// Acme appreciates your interest in its technology, please contact xyz@acme.com
// for technical support, and www.acme.com/emergingTech for updates and RSS feed.
#endif

Note: Obviously, you'll need to sort out a way to set the input/output files but that shouldn't be too difficult.

Disclosure: I am the original author of pypreprocessor.

Aside: I originally wrote it as a solution to the dreaded python 2k/3x maintenance issue. My approach was, do 2 and 3 development in the same source files and just include/exclude the differences using preprocessor directives. Unfortunately, I discovered the hard way that it's impossible to write a true pure (ie doesn't require c) preprocessor in python because the lexer flags syntax errors in incompatible code before the preprocessor gets a chance to run. Either way, it's still useful under a wide range of circumstances including yours.


问:
Project/DLL separation of concerns in ASP.NET MVC
I'm coming from a web forms n-tier background into ASP.NET MVC projects, and I'm wondering what the best practices are for separation of the components of MVC into different libraries (or not to) in the way one might with an n-tier model. Most of the sample apps I have seen only had one project file and objects were separated only by folder.

Thanks

答:
A typical multi-tier application looks like this:

In an MVC application, the data tier and logic tier reside in the Model, while the presentation tier resides in the View.  In between the Model and the View, the Controller provides a switchyard, routing web requests and responses to the appropriate methods, views and model logic.

Within the Model, you can have as many or as few libraries as you like.  For the View and the Controllers, I would say a good rule of thumb is one DLL per web application or service.  Services might include a REST web API for external applications.

The Model typically contains at least three things: the database, the Business Logic, and a Service Layer.  The Service Layer is implemented as a series of classes and methods that represent the domain objects called Repositories.  Within these Repositories, it is not uncommon to use an ORM to provide object-level abstraction for the database.

Rules of thumb: Fat Model, thin controllers.  The View historically has as little domain logic as possible, although nowadays the web interfaces are getting smarter from a client-side standpoint, with jQuery, HTML5 and sophisticated client-side frameworks like Kendo.

ContentLicense: CC BY-SA 3.0


问:
Dealing with curly brace soup
I've programmed in both C# and VB.NET for years, but primarily in VB. I'm making a career shift toward C# and, overall, I like C# better.

One issue I'm having, though, is curly brace soup. In VB, each structure keyword has a matching close keyword, for example:

Namespace ...
    Class ...
        Function ...
            For ...
                Using ...
                    If ...
                        ...
                    End If
                    If ...
                        ...
                    End If
                End Using
            Next
        End Function
    End Class
End Namespace
```

<p>The same code written in C# ends up very hard to read:</p>

<pre class="lang-csharp prettyprint-override"><code>namespace ... {
    class ... {
        function ... {
            for ... {
                using ... {
                    if ... {
                        ...
                    }
                    if ... {
                        ...
                    }
                }
            }
            // wait... what level is this?
        }
    }
}
</code>```

Being so used to VB, I'm wondering if there's a technique employed by c-style programmers to improve readability and to ensure that your code ends up in the correct "block". The above example is relatively easy to read, but sometimes at the end of a piece of code I'll have 8 or more levels of curly braces, requiring me to scroll up several pages to figure out which brace ends the block I'm interested in.

答: If you are using an IDE, Just press Crtl + k + D and the IDE will do the rest of the work.

Title: Dealing with curly brace soup


问:
Should unit test be in separated repository?
Should I put unit testing stuffs in a separate repository, not in the same repository as the programming library?
So I reference the programming library as submodule.
But most open source projects that I have seen do not organize the projects like what I mention above.
Can anyone explain which approach is better?</p>

答:
You should put the unit tests in the same repository because otherwise someone has to answer to the question "Where are the tests?" every time the project is handed over from one person to another. References to other repositories tend to get invalid over time when repositories are relocated and people change from one version control system to another.

Just keep the tests close to the code.


问:
How can I best manage making open source code releases from my company's confidential research code?
My company (let's call them Acme Technology) has a library of approximately one thousand source files that originally came from its Acme Labs research group, incubated in a development group for a couple years, and has more recently been provided to a handful of customers under non-disclosure.  Acme is getting ready to release perhaps 75% of the code to the open source community.  The other 25% would be released later, but for now, is either not ready for customer use or contains code related to future innovations they need to keep out of the hands of competitors.

The code is presently formatted with #ifdefs that permit the same code base to work with the pre-production platforms that will be available to university researchers and a much wider range of commercial customers once it goes to open source, while at the same time being available for experimentation and prototyping and forward compatibility testing with the future platform.  Keeping a single code base is considered essential for the economics (and sanity) of my group who would have a tough time maintaining two copies in parallel.

Files in our current base look something like this:

```<code>> // Copyright 2012 (C) Acme Technology, All Rights Reserved.
> // Very large, often varied and restrictive copyright license in English and French,
> // sometimes also embedded in make files and shell scripts with varied
> // comment styles.
>
>
>   ... Usual header stuff...
>
> void initTechnologyLibrary() {
>     nuiInterface(on);
> #ifdef  UNDER_RESEARCH
>     holographicVisualization(on);
> #endif
> }
</code>```

And we would like to convert them to something like:

```<code>> // GPL Copyright (C) Acme Technology Labs 2012, Some rights reserved.
> // Acme appreciates your interest in its technology, please contact xyz@acme.com
> // for technical support, and www.acme.com/emergingTech for updates and RSS feed.
>
>   ... Usual header stuff...
>
> void initTechnologyLibrary() {
>     nuiInterface(on);
> }
</code>```

Is there a tool, parse library, or popular script that can replace the copyright and strip out not just #ifdefs, but variations like #if defined(UNDER_RESEARCH), etc.?

The code is presently in Git and would likely be hosted somewhere that uses Git.  Would there be a way to safely link repositories together so we can efficiently reintegrate our improvements with the open source versions?  Advice about other pitfalls is welcome.

答:
I'm not going to show you a tool to convert your codebase, plenty of answers already did that. Rather, I'm answering your comment about how to handle branches for this.

You should have 2 branches:

Community (let's call the open source version like this)

Professional (let's call the closed source version like this)

The preprocessors shouldn't exist. You have two different versions. And a cleaner codebase overall.

You're afraid of maintaining two copies in parallel? Don't worry, you can merge!

If you're making modifications to the community branch, just merge them in the professional branch. Git handles this really well.

This way, you keep 2 maintained copies of your codebase. And releasing one for open source is easy as pie.


问:
How to promote code reuse and documentation?
As a team lead of about 10+ developers, I would want to promote code reuse. We have written a lot of code-- a lot of them are repetitive over the past few years. The problem now is that a lot of these code are just duplicate of some other code or a slight variation of them.

I have started the movement ( discussion) on how to make code into components so that they can be reused for the future projects, but the problem is that I afraid the new developers or other developers who are ignorant of the components will just go forward and write their own thing.

Is there anyway to remind the developers to reuse the components/ improve the documentation/ contribute to the underlying component instead of duplicating the existing code and tweaking on it or just write their own?

How to make the components easily discover-able, easily usable so that everyone will use it?

I think every developer knows about the benefit of reusable components and wants to use them, it's just that we don't know how to make them discoverable. Also, the developers when they are writing code, they know they should write reusable code but lack of the motivation to do so.

答:
You need documentation, a proper one. It should be easy to find and navigate. You also need discipline. If there's already a solution provided in your reusable code libraries but the developer chooses to use his own solution instead (without any proper reason), you should revert his solution and tell him to use the existing solution.

I also agree with Euphoric's comment to the question. It's often impossible to reuse anything between different projects (usually all the CRUD operations look the same, but usually you can't reuse them).


问:
Pattern for a class that does only one thing
Let's say I have a procedure that does stuff:

```<code>void doStuff(initalParams) {
    ...
}
</code>```

Now I discover that "doing stuff" is quite a compex operation. The procedure becomes large, I split it up into multiple smaller procedures and soon I realize that having some kind of state would be useful while doing stuff, so that I need to pass less parameters between the small procedures. So, I factor it out into its own class:

```<code>class StuffDoer {
    private someInternalState;

    public Start(initalParams) {
        ...
    }

    // some private helper procedures here
    ...
}
</code>```

And then I call it like this:

```<code>new StuffDoer().Start(initialParams);
</code>```

or like this:

```<code>new StuffDoer(initialParams).Start();
</code>```

And this is what feels wrong. When using the .NET or Java API, I always never call new SomeApiClass().Start(...);, which makes me suspect that I'm doing it wrong. Sure, I could make StuffDoer's constructor private and add a static helper method:

```<code>public static DoStuff(initalParams) {
    new StuffDoer().Start(initialParams);
}
</code>```

But then I'd have a class whose external interface consists of only one static method, which also feels weird.

Hence my question: Is there a well-established pattern for this type of classes that

have only one entry point and

have no "externally recognizable" state, i.e., instance state is only required during execution of that one entry point?

答:
I would say that the class in question (using a single entry point) is well designed. It's easy to use and extend. Quite SOLID.

Same thing for no "externally recognizable" state. It's good encapsulation.

I don't see any problem with code like:

```<code>var doer = new StuffDoer(initialParams);
var result = doer.Calculate(extraParams);
</code>```

Body:
I would say that the class in question (using a single entry point) is well designed. It's easy to use and extend. Quite SOLID.

Same thing for no "externally recognizable" state. It's good encapsulation.

I don't see any problem with code like:

var doer = new StuffDoer(initialParams);
var result = doer.Calculate(extraParams);


答:
```<code>new StuffDoer().Start(initialParams);
</code>```

There is a problem with clueless developers who could use a shared instance and use it

multiple times (ok if previous (maybe partial) execution does not mess up later execution)

from multiple threads (not OK, you explicitly said it has internal state).

So this needs explicit documentation that it is not thread safe and if it's lightweight (creating it is fast, does not tie up external resources nor lot of memory) that it's OK to instantiate on the fly.

Hiding it in a static method helps with this, because then reusing the instance never happen.

If it has some expensive initialization, it could (it isn't always) be beneficial to prepare initializing it once and using it multiple times by creating another class that would contain state only and make it cloneable. Initialization would create state that would be stored in doer. start() would clone it and pass it to internal methods.

This would also allow for other things like persisting state of partial execution. (If it takes long and external factors, e.g. electricity supply failure, could interrupt execution.) But these additional fancy things are usually not needed, so not worth it.

Title: Pattern for a class that does only one thing

Body:
Let's say I have a procedure that does stuff:

```<code>void doStuff(initalParams) {
    ...
}
</code>```

Now I discover that "doing stuff" is quite a compex operation. The procedure becomes large, I split it up into multiple smaller procedures and soon I realize that having some kind of state would be useful while doing stuff, so that I need to pass less parameters between the small procedures. So, I factor it out into its own class:

```<code>class StuffDoer {
    private someInternalState;

    public Start(initalParams) {
        ...
    }

    // some private helper procedures here
    ...
}
</code>```

And then I call it like this:

```<code>new StuffDoer().Start(initialParams);
</code>```

or like this:

```<code>new StuffDoer(initialParams).Start();
</code>```

And this is what feels wrong. When using the .NET or Java API, I always never call new SomeApiClass().Start(...);, which makes me suspect that I'm doing it wrong. Sure, I could make StuffDoer's constructor private and add a static helper method:

```<code>public static DoStuff(initalParams) {
    new StuffDoer().Start(initialParams);
}
</code>```

But then I'd have a class whose external interface consists of only one static method, which also feels weird.

Hence my question: Is there a well-established pattern for this type of classes that

have only one entry point and

have no "externally recognizable" state, i.e., instance state is only required during execution of that one entry point?

Body:
new StuffDoer().Start(initialParams);

There is a problem with clueless developers who could use a shared instance and use it

multiple times (ok if previous (maybe partial) execution does not mess up later execution)

from multiple threads (not OK, you explicitly said it has internal state).

So this needs explicit documentation that it is not thread safe and if it's lightweight (creating it is fast, does not tie up external resources nor lot of memory) that it's OK to instantiate on the fly.

Hiding it in a static method helps with this, because then reusing the instance never happen.

If it has some expensive initialization, it could (it isn't always) be beneficial to prepare initializing it once and using it multiple times by creating another class that would contain state only and make it cloneable. Initialization would create state that would be stored in doer. start() would clone it and pass it to internal methods.

This would also allow for other things like persisting state of partial execution. (If it takes long and external factors, e.g. electricity supply failure, could interrupt execution.) But these additional fancy things are usually not needed, so not worth it.


问:
Why is Java version 1.X referred to as Java X?
I saw that Java 1.2 is also known as Java 2. Do "Java 1.x" and "Java x" (for example "Java 1.6" and "Java 6") refer to the same version of Java?

And if yes, why the need for this duality?

答:
The short answer: Marketing.

A longer answer:
The short form (e.g. Java 6) is the so-called "product version" and is how Java is marketed to users and in press releases, etc.

The longer form (e.g. Java 1.6.0) is the "developer version". It is used internally, and will also be encountered by Java developers (e.g. The java.version system property uses the long form).

See these pages for more information:

http://www.oracle.com/technetwork/java/javase/namechange-140185.html

http://www.oracle.com/technetwork/java/javase/version-6-141920.html


答:
Because book with title "Learn Shiny New Java 3" will be sold out earlier than book with title "What's new in Java 1.3".

So yes, it is mainly marketing reasons. On the other hand, I don't see a severe crime here. After all, in some products, like Mozilla or Chrome, major build number is constantly get incremented, and others stick to incrementing minor build number, though, sometimes, there are big changes coming up with each new release.

Some, like Apple, don't want to leave us, users, with dull names like "Mac OS 10.6".

And Sun used to be OK with N alias instead of introducing "Java Green Diplodocus" release.

Title: Why is Java version 1.X referred to as Java X?

Body:
I saw that Java 1.2 is also known as Java 2. Do "Java 1.x" and "Java x" (for example "Java 1.6" and "Java 6") refer to the same version of Java?

And if yes, why the need for this duality?


答:
TheServerSide explains change from "Java 1.x" to "Java x" as follows:

Sun has cut off the "1." to change J2SE 1.5.0 to J2SE 5.0. The reason for the change? Sun claims that "this is the most significant upgrade to the Java platform and programming language since its initial release nearly one decade ago", and that this version is worthy.

Apparently there were talks to rename to "J5SE", but there was thought that the J2EE brand means too much to change.

Aren't version numbers fun?

Read the press release: Sun introduces most significant and advanced Java platform release in 5 years

Note link in above quote is killed by Oracle. As far as I can tell, it is available at prnewswire:

Sun Microsystems, Inc. (Nasdaq:   SUNW), the creator

   and leading advocate of Java(TM) technology, today introduced Java 2 Platform

   Standard Edition (J2SE(TM)) 5.0, the most significant upgrade to the Java

   platform and programming language since its initial release nearly one decade

   ago. Known as Project Tiger, this updated Java platform offers dramatic ease

   of development, new application monitoring and management features, a

   dedicated focus on rich client support for the PC desktop and record-breaking

   performance...

For the sake of completeness note that 1.X version style hasn't been completely dropped.

"Version 1.5.0" Used by Developers

J2SE also keeps the version number 1.5.0 (or 1.5) in some places that are visible only to developers, or where the version number is parsed by programs. As mentioned, 1.5.0 refers to exactly the same platform and products numbered 5.0...

Also note that as pointed in comments term "J2SE" used above has been later changed to "Java SE".


答:
I think the best way to actually make them reuse code is motivation. If you put the reusable components in extra projects, like Euphoric suggested, put much effort in it. Where I work, we made a project, that runs a set of predefined interfaces in configurable executionplans and provides a few services (e.g. different classes for DB_interaction, an FTP-Service, ...).
The project is a big success, because our developers actually want to use the micro-framework, because it is saving them a lot of time for writing boilerplate-code for similar projects. The same thing is for Utility-libraries for Lists, Strings, etc., but in this case you would want to use existing once. (why reinvent the weel?)

Conclusion: Let your developers experience the benefits of well-tested reusable components. But I also agree with the answer of Andrzej Bobak: Many things aren't reusable, because they are similar, but not the same.

Title: How to promote code reuse and documentation?

Body:
As a team lead of about 10+ developers, I would want to promote code reuse. We have written a lot of code-- a lot of them are repetitive over the past few years. The problem now is that a lot of these code are just duplicate of some other code or a slight variation of them.

I have started the movement ( discussion) on how to make code into components so that they can be reused for the future projects, but the problem is that I afraid the new developers or other developers who are ignorant of the components will just go forward and write their own thing.

Is there anyway to remind the developers to reuse the components/ improve the documentation/ contribute to the underlying component instead of duplicating the existing code and tweaking on it or just write their own?

How to make the components easily discover-able, easily usable so that everyone will use it?

I think every developer knows about the benefit of reusable components and wants to use them, it's just that we don't know how to make them discoverable. Also, the developers when they are writing code, they know they should write reusable code but lack of the motivation to do so.


答:
There's a pattern called Method Object where you factor out a single, large method with a lot of temporary variables / arguments into a separate class. You do this rather than just extracting parts of the method out into separate methods because they need access to the local state (the parameters and temporary variables) and you can't share the local state using instance variables because they would be local to that method (and the methods extracted from it) only and would go unused by the rest of the object.

So instead, the method becomes its own class, the parameters and temporary variables become instance variables of this new class, and then the method gets broken up into smaller methods of the new class. The resulting class usually has just a single public instance method that performs the task the class encapsulates.


答:
Sun Microsystems had back then a bad habit of going through numerous naming changes for its products, and to use confusing name to start with in the first place.

What's in a Name, or what does "Java" Mean?

Originally the term "Java" was being used to describe indiscriminately:

the language,

the platform,

and some others happened to refer to the JVM and the Java Class Lib as just Java as well.

Internal and External Number

With regard to version numbers, as others pointed out it was partly because of marketing, and partly because they simply felt like Java had done such progress a major version upgrade was better suited (for Java 1.2 / Java 2, and when Java 1.5 / Java 5).

So, what we call Java 2 was actually Java 1.2 to 1.4. Java 3 and Java 4 never existed, and we skipped directly to Java 5, as they tried to explain here (from this page on naming and versioning).

I was also probably a little as well to not mess with their internal numbering used in their tracking and development systems. I tend to think of it as 1.x = language version and X = language and product version. It makes sense, as normal users do not need to worry about minor increments and updates, as they encourage automatic updates, and these shouldn't introduce any changes to the language or the bytecode.

Note also that it gets weirder when you look at minor versions and update numbers. For instance, we had a Java 1.3.1 and later Java 1.4.1 and 1.4.2.

Updates

However, there were no 1.x.y ever since, it's always been 1.x.0_UPDATE:

Java 5 had updates up to 1.5.0_22,

Java 6 is - so far - up to 1.6.0_37,

Java 7 is - so far - up to 1.7.0_09.

Note also that you will also see updates refered to with either of these naming conventions:

like 1.5.0_22 or 1.7.0_04 (note the padding 0s on the update version, aligning on 2 digits),

but also 1.5.0u22 or 1.7.0u4 (note the padding 0s are gone, yay!).

And for extra confusion and to keep up with Sun Microsystems' tradition, Oracle now drops announcements like this.

Product Names

Note also that not only did they get into the habit of changing the numbering, but also the names of the product offerings. So, Java 2 have J2SE (Java 2 Standard Edition), J2EE (Java 2 Enterprise Edition) and J2ME (Java 2 Mobile Edition). Since the introduction of Java 5, these conventions and acronyms have been dropped (though some have an incredibly long resilience, mostly thanks for dumb recruitment agencies who have no clue what they are talking about) in favor of Java SE, Java EE and Java ME, which are sometimes abbreviated - but shouldn't officially - to JSE, JEE (fairly common) and JME.

Your read this page for more information about the current versioning system used by Sun Microsystems and now Oracle since Java 1.3.1.

(For bonus points, try to lookup the history of NetBeans now to see that it was also renamed a few times).

They Don't Know Themselves

They're also struggling to decide whether they should back-update existing references or not. For instance, this page about older releases uses the old numbering system for old releases, but the newer product names (Java SE 1.1, 1.2, 1.3 and 1.4 were not released with this naming convention).

Maybe they're just screwing with us for fun. Who knows?

What About the JVMS and JLS?

They had fun with naming and numbering there too, of course.

The Java Language Specification used to be released with a book "edition" versioning syste,, following product numbers. So:

Java 1 had its "Java Language Specification",

Java 2 had its "Java Language Specification, 2nd edition".

So far, so good.

Except the "Java Language Specification" was later only re-edited when language changes were introduced in Java 5 (which kind of make sense, you won't publish new book editions just for fun). As this was the 3rd time they were editing it, they called it (tada!) "Java Langauge Specification, 3rd edition".

But obviously, people then started to wonder why 1.3 and 1.4 didn't have a language spec, or why Java 5 was matched with a 3rd edition of the language spec.

So, Java 7 is now just calling it the "Java Language Specification, Java SE 7 Edition", though we often refer to this one as JLS7 for shorthand and to avoid RSI.

They're Not the Only Ones...

For additional fun, look at Microsoft Windows RT's naming fail, or Apple's naming and numbering madness with iPhones, iPads or even iPods.


问:
How do I trust an off site application
I need to implement something similar to a license server. This will have to be installed off site at the customers' location and needs to communicate with other applications at the customers' site (the applications that use the licenses) and an application running in our hosting center (for reporting and getting license information).

My question is how to set this up in a way I can trust that:

The license server is really our application and not something that just simulates it; and

There is no "man in the middle" (i.e. a proxy or something that alters the traffic).

The first thing I thought of was to use with client certificates and that would solve at least 2. However, what I'm worried about is that someone just decompiles (this is build in .NET) the license server, alters some logic and recompiles it. This would be hard to detect from both connecting applications.

This doesn't have to be absolutely secure since we have a limited number of customers whom we have a trust relationship with. However, I do want to make it more difficult than a simple decompile/recompile of the license server. I primarily want to protect against an employee or nephew of the boss trying to be smart.

答:
Two possibilities come to mind:

Have the license server run on a physically secured box you provide

Have the license server be a dumb proxy through which the other applications communicate with your hosted license app, basically a VPN tunnel.

If you just think decompiling a .net app is a bit too easy, compile it to native or use an obfuscator. But I think you're probably worrying needlessly. The scenario that someone at a company you have a "trust relationship" with would have the necessariy skills, the motivation and the willingness to commit a crime seems very unlikely to me.

Title: How do I trust an off site application


答: You want the version of the tests to match the version of the code, so that implies you keep the tests in the same repository as the code.  That goes for automatic code generation scripts, build scripts, etc. too.</p>

Title: Should unit test be in separated repository?

Body:
Should I put unit testing stuffs in a separate repository, not in the same repository as the programming library?
So I reference the programming library as submodule.
But most open source projects that I have seen do not organize the projects like what I mention above.
Can anyone explain which approach is better?</p>


答:
From a SOLID principles perspective jgauffin's answer makes sense. However, you shouldn't forget about the general design principles e.g. information hiding.

I see several problems with the given approach:

As you pointed out yourself people don't expect to use the 'new' keyword, when the object created doesn't manage any state. Your design reflects it's intention. People using your class might get confused as to what state it manages, and whether subsequent calls to the method might result in different behavior.

From the perspective of the person using the class the inner state is well hidden, but when wanting to make modifications to the class or simply understanding it, you are making things more complex. I have already written a lot about the problems I see with splitting methods just to make them smaller, especially when moving state to the class scope. You are modifying the way your API should be used just in order to have smaller functions! That in my opinion is definitely taking it too far.

Some related references

Possibly a main point of argument lies in how far to stretch the Single Responsibility Principle. "If you take it to that extreme and build classes that have one reason to exist, you may end up with only one method per class. This would cause a large sprawl of classes for even the most simple of processes, causing the system to be difficult to understand and difficult to change."

Another relevant reference relating to this topic: "Divide your programs into methods that perform one identifiable task. Keep all of the operations in a method at the same level of abstraction." - Kent Beck Key here is "the same level of abstraction". That doesn't mean "one thing", as it is often interpreted. This level of abstraction is entirely up to the context for which you are designing.

So what is the proper approach?

Without knowing your concrete use case it is hard to tell. There is a scenario in which I sometimes (not often) use a similar approach. When I want to process a dataset, without wanting to make this functionality available to the entire class scope. I wrote a blog post about it, how lambdas can even further improve encapsulation. I also started a question on the topic here on Programmers. The following is a latest example of where I used this technique.

```<code>new TupleList<Key, int>
{
    { Key.NumPad1, 1 },
            ...
    { Key.NumPad3, 16 },
    { Key.NumPad4, 17 },
}
    .ForEach( t =>
    {
        var trigger = new IC.Trigger.EventTrigger(
                        new KeyInputCondition( t.Item1, KeyInputCondition.KeyState.Down ) );
        trigger.ConditionsMet += () => AddMarker( t.Item2 );
        _inputController.AddTrigger( trigger );
    } );
</code>```

Since the very 'local' code within the ForEach isn't reused anywhere else, I can simply keep it in the exact location where it is of relevance. Outlining code in such a way that code which relies on each other is strongly grouped together makes it more readable in my opinion.

Possible alternatives

In C# you could use extension methods instead. So operate on the argument directly you pass to this 'one thing' method.

See whether this function actually doesn't belong to another class.

Make it a static function in a static class. This most likely is the most appropriate approach, as is also reflected in the general APIs you referred to.

Body:
From a SOLID principles perspective jgauffin's answer makes sense. However, you shouldn't forget about the general design principles e.g. information hiding.

I see several problems with the given approach:

As you pointed out yourself people don't expect to use the 'new' keyword, when the object created doesn't manage any state. Your design reflects it's intention. People using your class might get confused as to what state it manages, and whether subsequent calls to the method might result in different behavior.

From the perspective of the person using the class the inner state is well hidden, but when wanting to make modifications to the class or simply understanding it, you are making things more complex. I have already written a lot about the problems I see with splitting methods just to make them smaller, especially when moving state to the class scope. You are modifying the way your API should be used just in order to have smaller functions! That in my opinion is definitely taking it too far.

Some related references

Possibly a main point of argument lies in how far to stretch the Single Responsibility Principle. "If you take it to that extreme and build classes that have one reason to exist, you may end up with only one method per class. This would cause a large sprawl of classes for even the most simple of processes, causing the system to be difficult to understand and difficult to change."

Another relevant reference relating to this topic: "Divide your programs into methods that perform one identifiable task. Keep all of the operations in a method at the same level of abstraction." - Kent Beck Key here is "the same level of abstraction". That doesn't mean "one thing", as it is often interpreted. This level of abstraction is entirely up to the context for which you are designing.

So what is the proper approach?

Without knowing your concrete use case it is hard to tell. There is a scenario in which I sometimes (not often) use a similar approach. When I want to process a dataset, without wanting to make this functionality available to the entire class scope. I wrote a blog post about it, how lambdas can even further improve encapsulation. I also started a question on the topic here on Programmers. The following is a latest example of where I used this technique.

new TupleList<Key, int>
{
    { Key.NumPad1, 1 },
            ...
    { Key.NumPad3, 16 },
    { Key.NumPad4, 17 },
}
    .ForEach( t =>
    {
        var trigger = new IC.Trigger.EventTrigger(
                        new KeyInputCondition( t.Item1, KeyInputCondition.KeyState.Down ) );
        trigger.ConditionsMet += () => AddMarker( t.Item2 );
        _inputController.AddTrigger( trigger );
    } );

Since the very 'local' code within the ForEach isn't reused anywhere else, I can simply keep it in the exact location where it is of relevance. Outlining code in such a way that code which relies on each other is strongly grouped together makes it more readable in my opinion.

Possible alternatives

In C# you could use extension methods instead. So operate on the argument directly you pass to this 'one thing' method.

See whether this function actually doesn't belong to another class.

Make it a static function in a static class. This most likely is the most appropriate approach, as is also reflected in the general APIs you referred to.


答:
Some hints:

Use a password when signing your assemblies (you're signing them, aren't you?).

Provide an automatic update feature of the licensing server. The client company would have to choose between:

Keeping patching each new version of the licensing server with a hacker patch,

Disabling auto-update, given that if they contact your support one day, they would have a hard time explaining why are they disabling the free of charge updates,

Spending days automating the patching.

Provide a mixed licensing solution. For example the local licensing server serves only as a caching/proxy solution, while communicating directly with your own server when online. The local server validates the licenses itself only when offline, given that it will stop functioning if it is offline for too long.

For example, it would happen like this:

Client requests to validate the license,

Intermediary licensing server forwards the request to your own server,

Your own server responds that the license is valid,

Intermediary licensing server remembers that the license is valid (using hashes etc. to avoid being tampered easily),

The next time, if the intermediary licensing server is requested to validate the same license, if it is online, it still does a request to your own server. If it is offline, it checks for local cache.

If a different license (i.e. something which doesn't happen very often: either new software is installed or old software is deployed on a new machine) is requested and the intermediary licensing server is offline, it returns an error saying that it is impossible to validate the new license offline.

Rely on support. If the client is requesting for support, ask to install a tool which will collect and send you the information about the system (current version of the licensing server, etc.). This tool may also compute the hashes of the executable files of the licensing server; if they don't validate, the customer would have to explain why he changed those files, while it is explicitly forbidden by the license.

Obfuscate the code.

Actively report hacking attempts. For example, you don't need to hide the core licensing validation process; call it LicenseValidation.dll for example. But the original code which should run the code within LicenseValidation.dll should start by computing the hash of the file, and if it's wrong, report it to you.

There are chances that a lazy hacker will start by tampering the most obvious file, while forgetting to verify if the file is validated somewhere else.

Gather statistics. With lots of statistics which are primarily not intended to detect piracy (like profiling results or crash reports), you can still have some hints that a precise company has a large degree of piracy.

For example if the licensing server reports that the piece of software A is installed on two PCs, while you constantly received for the last two months profiler reports from twenty static IP addresses (same IP, same machine name, same OS, etc.), it's a good sign that something goes wrong there.

Have competitive pricing. Few companies would spend time hacking a CRM which costs $50 per user. If the same CRM costs $50 000 per server and the company expands to ten other servers, it's rather advantageous to hire a skillful hacker.

Title: How do I trust an off site application

Body:
I need to implement something similar to a license server. This will have to be installed off site at the customers' location and needs to communicate with other applications at the customers' site (the applications that use the licenses) and an application running in our hosting center (for reporting and getting license information).

My question is how to set this up in a way I can trust that:

The license server is really our application and not something that just simulates it; and

There is no "man in the middle" (i.e. a proxy or something that alters the traffic).

The first thing I thought of was to use with client certificates and that would solve at least 2. However, what I'm worried about is that someone just decompiles (this is build in .NET) the license server, alters some logic and recompiles it. This would be hard to detect from both connecting applications.

This doesn't have to be absolutely secure since we have a limited number of customers whom we have a trust relationship with. However, I do want to make it more difficult than a simple decompile/recompile of the license server. I primarily want to protect against an employee or nephew of the boss trying to be smart.


问:
Do people in non-English-speaking countries code in English?
I've heard it said (by coworkers) that everyone "codes in English" regardless of where they're from. I find that difficult to believe, however I wouldn't be surprised if, for most programming languages, the supported character set is relatively narrow.

Have you ever worked in a country where English is not the primary language?

If so, what did their code look like?

答:
I (dutchy) always code in English, it just makes much more sense, all the language keywords, etc. are in English, so why not code the rest in English? :)

I always put all comments in English as well. You never know who will have to edit your code, they might not speak your native language.

OwnerDisplayName: StarLite


问:
Adhering to a protocol and being a subclass at the same time?
In objective C, I have a situation where I would like to have an abstract protocol (interface) with 5 methods and 4 properties, but at the same time, I'd like to have a common implementation of 3 of those 5 methods.

So my question is, is it ok to

1) have just an interface declaration with all the method and property declarations,

2) have a base class that adheres to that protocol (implements that interface) but also provides a common implementation of some of those classes, and only has empty stub method implementations for the rest of the methods, and then finally,

3) have a bunch of subclasses (from that base class), that will conform to that protocol - but - also inherit common method implementations -and - implement on their own those stub methods?

答:
This is the pattern that is often used to address the lack of abstract classes in Objective C.

It is very common for the missing method stubs of the base implementation to raise an exception, to make sure that you catch incomplete implementations. See this answer on stack overflow for details of how it is commonly done.


问:
Learning new programming languages and technologies
Some time ago I was to learn iOS development at my work. I didn't manage to learn it because I was moved to more important task with another technology already familiar to me. But the short time I  spent on iOS, I felt that I could do better if I spent a few hours at the workplace during which I could discuss some matters concerning iOS with my colleagues who know it, and the rest of the time working at home.

I think many developers would share my opinion and prefer to learn the new technology at home.

Is there any accepted practice? Has any developer had an experience when the company encouraged the developers to choose where they feel more comfortable to learn new technologies?

答:
We adopted so called FedEx days. Any team member is allowed to spend all working day for learning. Once per several weeks. Then he has to make some little project/presentation and share his knowledge with colleagues.

Learning at home is natural I believe to most of the professionals. But I feel lerning under some preassure of responsibility is more efficient.


答: I would say it's pretty good, but that your API should still be a static method on a static class, since that's what the user expects.  The fact that the static method uses new to create your helper object and do the work is an implementation detail that should be hidden from whoever is calling it.


答:
Beside the already mentioned factors "documentation", "easy to find and navigate", "discipline" and "codereview"

resusable code must be

easy to use (= need examples i.e. unittests)

without too many dependencies to other modules and

it must have a stable api so i donot have to update my aplication to use the library.

without the last two items it is much easier to use "copy&past-inheritance" that we do not want.


答:
is, is it ok to

1) have just an interface declaration with all the method and property
  declarations,

Try it. You'll find that without an @implementation section for any classes you use (even if you're only subclassing them) you get an error. You need an @implementation for each class.

2) have a base class that adheres to that protocol (implements that
  interface) but also provides a common implementation of some of those
  classes, and only has empty stub method implementations for the rest
  of the methods

Yes, you can certainly do that. Throw an exception in the stubs if you want to force subclasses to override them.

3) have a bunch of subclasses (from that base class), that will
  conform to that protocol - but - also inherit common method
  implementations -and - implement on their own those stub methods?

Sure, no problem there.

A protocol really is just a way to specify a set of methods. When you adopt a protocol in your class, you're promising to provide those methods in your class, but you're not promising anything about how those methods are implemented -- the compiler won't complain if they're just empty methods that you override in subclasses.

Another possibility is to implement the common methods in your base class without adopting the protocol in question. Then adopt the protocol in each of your subclasses and implement any methods that you don't inherit from the base class. That might not seem ideal, since each subclass has to adopt the protocol, but it may more accurately reflect the way the code works: the base class doesn't adopt the protocol, only the subclasses do. If you happen to instantiate the base class and send it a -conformsToProtocol: message, you'll get NO back.

Title: Adhering to a protocol and being a subclass at the same time?

Body:
In objective C, I have a situation where I would like to have an abstract protocol (interface) with 5 methods and 4 properties, but at the same time, I'd like to have a common implementation of 3 of those 5 methods.

So my question is, is it ok to

1) have just an interface declaration with all the method and property declarations,

2) have a base class that adheres to that protocol (implements that interface) but also provides a common implementation of some of those classes, and only has empty stub method implementations for the rest of the methods, and then finally,

3) have a bunch of subclasses (from that base class), that will conform to that protocol - but - also inherit common method implementations -and - implement on their own those stub methods?


问:
What does it mean to write "good code"?
In this question I asked whether being a bad writer hinders you from writing good code. Many of the answers started of with "it depends on what you mean by good code".

It appears that the term "good code" and "bad code" are very subjective. Since I have one view, it may be very different from others' view of them.

So what does it mean to write "good code"? What is "good code"?

答:
Let me kindly disagree on the readibility. No, not completely: Good code should be readable, and that can be easily achieved with enough comments.

But I consider two kinds of WTF: those where you wonder if the programmer got further than programming 101, and those where you absolutely don't grasp the geniality of the code. Some code can look very strange at first, but is actually a very inventive solution to a hard problem. The second one shouldn't count in the WTF-meter, and can be avoided by comments.

Very readible code can be very, very slow. A less readible solution can give a manyfold improvement in speed. R is a great example of a language where that often is true. One likes to avoid for-loops there as much as possible. In general, I'd consider the fastest code the better code even though it's less readible. That is, if the improvement is substantial off course, and enough comments are inserted to explain what the code does.

Even more, memory management can be crucial in many scientific applications. Code that is very readible, tend to be kind of sloppy in memory usage: there are just more objects created. In quite some cases smart use of memory makes the code again less readible. But if you juggle around gigabytes of DNA sequences for example, memory is a crucial factor. Again, I consider the less memory-intensive code the better code, regardless of readibility.

So yes, readibility is important for good code. I know the adagium of Uwe Liggis : Thinking hurts and computers are cheap. But in my field (statistical genomics), computational times of a week and memory usage of over 40 Gb is not considered abnormal. So an improvement of twice the speed and half the memory is worth a lot more than that extra bit of readibility.

ContentLicense: CC BY-SA 2.5

Title: What does it mean to write "good code"?


答:
This is going to be difficult, because people like to write new code for simple components and they like doing it their way. It's much harder to leverage an existing solution and extend it, than to write a completely new implementation with the new requirements. What you need to do, as has been stated, is start a code review process among the team to help identify situations where an existing components should have been used/extented instead of a new one.

You also need to maintain a very good and thorough documentation so that people can refer to it and easily find what they need. If the documentation is incomplete or out of sync with the real thing, people will not be motivated to search through it or enhance it.

As the team lead, you should also encourage people to ask themselves if a similar component exists before creating their own and direct them to the documentation so they can look it up. Sure the code review process will catch it if someone missed an existing component, but what if they already put 10 hours of development in their own implementation? You need to avoid these situations by enforcing good research behavior in the team.


问:
When a function is called in Javascript, is there then an easy way to find where a function is declared in?
It would be great if some IDE offered the way to right mouse click when a function is called and have the immediate option to jump to the function when it is defined.

Is this possible in Javascript?

Maybe I've just been oblivious - is there a name for this technique?

答:
This really is never going to be possible with JavaScript.  Some IDE's do a "best guess", but it will never be perfect.  Since JavaScript uses a dynamic type system, it is impossible to perform static analysis to determine what a symbol is bound to until runtime.

The closest thing to this would be in-browser debugging tools such as Firebug or chrome's developer tools, which do allow this feature at runtime.


问:
Does the "one assertion per test" rule apply for checking initial conditions?
I've been thinking about unit testing best practices and have come across the one assertion per unit test rule.  I can see where this idea would help to isolate pieces of complex operations or verification when you have code like so:

```<code>private Place place;

@Test
public void test_whiteHouse(){
   place = new place(KnownPlaces.WHITEHOUSE);
   assertEquals("1600 Pennsylvania Avenue", place.getAddress());
   assertEquals("Washington", place.getCity());
   assertEquals("DC", place.getState());
}
</code>```

I see where you would generally want to break it into smaller tests like this:

```<code>private Place place;

@Before
public void setUp(){
   place = new place(KnownPlaces.WHITEHOUSE);
}

@Test
public void test_whiteHouse_street(){
   assertEquals("1600 Pennsylvania Avenue", place.getAddress());
}

@Test
public void test_whiteHouse_city(){
   assertEquals("Washington", place.getCity());
}

@Test
public void test_whiteHouse_state(){
   assertEquals("DC", place.getState());
}
</code>```

However, if I'm testing a setter, the code might look like this:

```<code>@Test
public void test_place_setCity(){
   String newCity = "timbuktu";
   Place place = new Place();
   place.setCity(newCity);
   assertEquals(newCity, place.getCity());
}
</code>```

The test will run properly, but if there's a shared setup, I'm making assumptions about the initial state.  What would be the downside on running a check on the initial state something like:

```<code>@Test
public void test_place_setCity(){
   String newCity = "timbuktu";
   Place place = new Place();
   assertFalse(place.getCity().equals(newCity));
   place.setCity(newCity);
   assertEquals(newCity, place.getCity());
}
</code>```

This check would verify that the setter method actually changed something by verifying the initial state was different than the final state.  Otherwise, a change or malfunction in a constructor or setup method could cause the test to become ineffective.  Are there any downsides to violating the one assert per constraint rule in this way?

答:
We have a policy where I work that uses an Assume class (provided by Nunit) for all these types of initial checks.  Further, we've made a wrapper around the assume class that forces the test writer to reference another test which explicitly tests the assumption.  I think I can better describe it with code:

```<code>@Test
public void test_place_setCity(){
   // Arrange
   String newCity = "timbuktu";
   Place place = new Place();
   Assume.That(place.getCity(), Is.Not.EqualTo(newCity), validatingTest:"test_new_place_should_not_have_city_set");

   // Act
   place.setCity(newCity);

   // Assert
   assertEquals(newCity, place.getCity());
}

@Test
public void test_new_place_should_not_have_city_set(){
   // Arrange
   // Nothing to Arrange

   // Act
   Place place = new Place();

   // Assert
   Assert.That(place.getCity(), Is.Empty, message:"New cities should not have a city initialized");
}
</code>```

So here, in our test_place_setCity test, we call Assume, and specify the name of the test that SHOULD fail if the assumption fails.  NUnit's assume class returns an "Inconclusive" rather than a "Failing" result when the condition does not succeed.  I think these pre-checks are important in many regards.  They let future maintainers know WHAT THE TEST ASSUMES to pass up front in an easy to understand way, they FAIL FAST when the assumption doesn't hold because they are at the top of the tests, and they give SEPERATE RESULTS for reporting purposes and to eliminate noise.  The name of another test is also a bonus for debugging.  Instead of trying to debug why a test won't run because an assumption fails, you can instead, easily navigate to the test that focuses on the assumption and debug using the more focused test.

Hopefully, you can find something in your testing framework to achieve all of these ideals, or else roll something yourself.  We've been using this methodology for a while and it's proved very useful.

Body:
We have a policy where I work that uses an Assume class (provided by Nunit) for all these types of initial checks.  Further, we've made a wrapper around the assume class that forces the test writer to reference another test which explicitly tests the assumption.  I think I can better describe it with code:

@Test
public void test_place_setCity(){
   // Arrange
   String newCity = "timbuktu";
   Place place = new Place();
   Assume.That(place.getCity(), Is.Not.EqualTo(newCity), validatingTest:"test_new_place_should_not_have_city_set");

   // Act
   place.setCity(newCity);

   // Assert
   assertEquals(newCity, place.getCity());
}

@Test
public void test_new_place_should_not_have_city_set(){
   // Arrange
   // Nothing to Arrange

   // Act
   Place place = new Place();

   // Assert
   Assert.That(place.getCity(), Is.Empty, message:"New cities should not have a city initialized");
}

So here, in our test_place_setCity test, we call Assume, and specify the name of the test that SHOULD fail if the assumption fails.  NUnit's assume class returns an "Inconclusive" rather than a "Failing" result when the condition does not succeed.  I think these pre-checks are important in many regards.  They let future maintainers know WHAT THE TEST ASSUMES to pass up front in an easy to understand way, they FAIL FAST when the assumption doesn't hold because they are at the top of the tests, and they give SEPERATE RESULTS for reporting purposes and to eliminate noise.  The name of another test is also a bonus for debugging.  Instead of trying to debug why a test won't run because an assumption fails, you can instead, easily navigate to the test that focuses on the assumption and debug using the more focused test.

Hopefully, you can find something in your testing framework to achieve all of these ideals, or else roll something yourself.  We've been using this methodology for a while and it's proved very useful.

ContentLicense: CC BY-SA 4.0


问:
Need advice on framework design: how to make extending easy
I'm creating a framework/library for a rather specific use-case (data type). It uses diverse spring components, including spring-data. The library has a set of entity classes properly set up and according service and dao layers. The main work or main benefit of the framework lies in the dao and service layer.

Developers using the framework should be able to extend my entity classes to add additional fields they require. Therefore I made dao and service layer generic so it can be used by such extended entity classes.

I now face an issue in the IO part of the framework. It must be able to import the according "special data type" into the database. In this part I need to create a new entity instance and hence need the actual class used. My current solution is to configure in spring a bean of the actual class used. The problem with this is that an application using the framework could only use 1 implementation of the entity (the original one from me or exactly 1 subclass but not 2 different classes of the same hierarchy.

I'm looking for suggestions / designs for solving this issue. Any ideas?

EDIT:

only idea I have is to add a parameter to the affected methods that takes a Class object. That would be the easy and pragmatic solution but it seems very ugly?

答:
Here my current solution I came up with after some research. But please also post your solutions.

I went with my suggestion in the above edit. However only the affected methods in the DAO require these additional parameters (in my case 2 java.lang.Class Objects). DAO and Service Classes remain generic.

The trick however is to add a Constructor to your Service Class which takes those 2 Class Object Parameters as arguments. Then in the Spring configuration you need to create a service bean per class in the hierarchy you want to use. Example:

```<code><bean id="myService1"  autowire="byName"
      class="MyServiceImpl">
    <constructor-arg index="0">
        <ref bean="CompoundClass"/>
    </constructor-arg>
    <constructor-arg index="1">
        <ref bean="CompoundQueryClass"/>
    </constructor-arg>
</bean>

<bean id="myService2"  autowire="byName"
      class="MyServiceImpl">
    <constructor-arg index="0">
        <ref bean="CompoundClass2"/>
    </constructor-arg>
    <constructor-arg index="1">
        <ref bean="CompoundQueryClass2"/>
    </constructor-arg>
</bean>
</code>```

where the referenced beans are Class objects created like this:

```<code><bean id="CompoundClass" class="java.lang.Class" factory-method="forName">
    <constructor-arg value="full.qualified.class.name"/>
</bean>
</code>```

While the affected methods are now a bit cluttered (many arguments) and passing around Class objects seems non-ideal to me (probably I'm wrong) a developer using the framework will not have to deal with the issue. He can create his extended entities and apply the correct configuration. I've created tests for his and the solution those seem to work as expected.

If CompoundClass2 extends CompoundClass (which uses @DiscriminatorColumn) and I call a query method from MyServiceImpl only CompoundClass2 objects are in the result even if a CompoundClass object would match the query too + the right type is returned. No casting needed.

Body:
Here my current solution I came up with after some research. But please also post your solutions.

I went with my suggestion in the above edit. However only the affected methods in the DAO require these additional parameters (in my case 2 java.lang.Class Objects). DAO and Service Classes remain generic.

The trick however is to add a Constructor to your Service Class which takes those 2 Class Object Parameters as arguments. Then in the Spring configuration you need to create a service bean per class in the hierarchy you want to use. Example:

<bean id="myService1"  autowire="byName"
      class="MyServiceImpl">
    <constructor-arg index="0">
        <ref bean="CompoundClass"/>
    </constructor-arg>
    <constructor-arg index="1">
        <ref bean="CompoundQueryClass"/>
    </constructor-arg>
</bean>

<bean id="myService2"  autowire="byName"
      class="MyServiceImpl">
    <constructor-arg index="0">
        <ref bean="CompoundClass2"/>
    </constructor-arg>
    <constructor-arg index="1">
        <ref bean="CompoundQueryClass2"/>
    </constructor-arg>
</bean>

where the referenced beans are Class objects created like this:

<bean id="CompoundClass" class="java.lang.Class" factory-method="forName">
    <constructor-arg value="full.qualified.class.name"/>
</bean>

While the affected methods are now a bit cluttered (many arguments) and passing around Class objects seems non-ideal to me (probably I'm wrong) a developer using the framework will not have to deal with the issue. He can create his extended entities and apply the correct configuration. I've created tests for his and the solution those seem to work as expected.

If CompoundClass2 extends CompoundClass (which uses @DiscriminatorColumn) and I call a query method from MyServiceImpl only CompoundClass2 objects are in the result even if a CompoundClass object would match the query too + the right type is returned. No casting needed.


问:
How do you protect your WCF service?
sometimes a programmer comes up with a brilliant idea to protect his/her webservice created with Windows Communication Foundation.

I would like to hear from you guys, which techniques do you use to protect your WCF service and avoid unauthorized users to consume it?

For example, you would:

avoid Impersonate, use it only if necessary

publish metadata information to prevent tampering

avoid memory consuption enforcing a maximum size quota

create a security context token to control number of sessions

答:
Yesterday, I found an article, a video and code about using API keys with WCF. I've got to lock down a publicly exposed web service as part of what we need to do in order to comply with PCI-DSS, and this looks like the right way to move forward. In the past, this app and webservice were used only by a VB4/5/6 (now .NET) desktop application, but the boss wants it opened up as a for-pay service to others.

One financial client used a scheme with a security information element in the SOAP header. This element had 4 attributes, one was the name of the application, the timestamp and guid elements were used to prevent replay attacks and the 4th attribute was a hash based on the name of the app, the timestamp and guid, along with a "secret" (think of a password) stored in the registry (for windows servers, or a special locked down file for unix-based servers, with different "passwords" for different application names). The "secret" (or password) was intended to prevent situations where a trojan in the datacenter would be able to make inappropriate calls, or respond to them. This was obviously not WCF as it had to support unix, windows and other operating systems in the data centers, but the technique was fascinating and could be used elsewhere. Because they used url-rewriting, the security information element would not show up in WSDLs, you had to know about it from documentation that only authorised folks received; if you added ?WSDL to the end of a webservice endpoint, you got a lie.

Title: How do you protect your WCF service?


答:
Besides my more elaborate, personalized other answer, I feel the following observation deserves a separate answer.

There are indications that you might be following the Poltergeists anti-pattern.

Poltergeists are classes with very limited roles and effective life
  cycles. They often start processes for other objects. The refactored
  solution includes a reallocation of responsibilities to longer-lived
  objects that eliminate the Poltergeists.

Symptoms And Consequences

Redundant navigation paths.

Transient associations.

Stateless classes.

Temporary, short-duration objects and classes.

Single-operation classes that exist only to “seed” or “invoke” other classes through temporary associations.

Classes with “control-like” operation names such as start_process_alpha.

Refactored Solution

Ghostbusters solve Poltergeists by removing them from the class hierarchy altogether. After their removal,
  however, the functionality that was “provided” by the poltergeist must
  be replaced. This is easy with a simple adjustment to correct the
  architecture.


问:
Constant values in the interface
Some time ago I have read two different books and each of them gives totally different answer for the question if it is a good pattern to define constant values in the interface (in java).

So I am curious of your opinions with some reasonable arguments.

Is it a good habit/ pattern to define constant values in interfaces in java?

Is it generally good, generally bad or it depends?

答:
I use constants in interface to have the same references when my programms have internal parameters, about all when thoses constants may change in next version,

 and I use enum otherwhere.

I have also a interface of usual constant by default, those constants are use if no other environment parameter given by some myFile.properties overwrite them.

Effective Java (2008) from Joshua Bloch give many tips about it.

OwnerDisplayName: Łukasz Rzeszotarski

Title: Constant values in the interface

OwnerDisplayName: cl-r


答:
Item 19 of Effective Java 2nd ed. recommends the following:

If the constants are strongly tied to an existing class or interface, you should add them to the class or interface...If the constants are best viewed as members of an enumerated type, you should export them with an enum type. Otherwise, you should export the constants with a noninstantiable utility class.

```<code>public class SomeConstants {
    private SomeConstants() { } // Private default constructor

    public static final double WEIRD_NUMBER = 123456.7;
    public static final int ANOTHER_NUMBER = 5;
}
</code>```

Edit: As with all things, exceptions exist. This case (constants and some methods need to be shared by external types) might be a good argument for using an interface in this manner.

Title: Constant values in the interface

Body:
Some time ago I have read two different books and each of them gives totally different answer for the question if it is a good pattern to define constant values in the interface (in java).

So I am curious of your opinions with some reasonable arguments.

Is it a good habit/ pattern to define constant values in interfaces in java?

Is it generally good, generally bad or it depends?

Body:
Item 19 of Effective Java 2nd ed. recommends the following:

If the constants are strongly tied to an existing class or interface, you should add them to the class or interface...If the constants are best viewed as members of an enumerated type, you should export them with an enum type. Otherwise, you should export the constants with a noninstantiable utility class.

public class SomeConstants {
    private SomeConstants() { } // Private default constructor

    public static final double WEIRD_NUMBER = 123456.7;
    public static final int ANOTHER_NUMBER = 5;
}

Edit: As with all things, exceptions exist. This case (constants and some methods need to be shared by external types) might be a good argument for using an interface in this manner.

OwnerDisplayName: E-Man


答: In your example, I would not make an assertion about the state of the object before calling the setter.  That is outside of the scope of what you are testing.  That should have been checked in the initialization tests.  The setter/getter test is checking only that functionality so that would be the only assertion that you need.</p>

Title: Does the "one assertion per test" rule apply for checking initial conditions?

Body:
I've been thinking about unit testing best practices and have come across the one assertion per unit test rule.  I can see where this idea would help to isolate pieces of complex operations or verification when you have code like so:

```<code>private Place place;

@Test
public void test_whiteHouse(){
   place = new place(KnownPlaces.WHITEHOUSE);
   assertEquals("1600 Pennsylvania Avenue", place.getAddress());
   assertEquals("Washington", place.getCity());
   assertEquals("DC", place.getState());
}
</code>```

I see where you would generally want to break it into smaller tests like this:

```<code>private Place place;

@Before
public void setUp(){
   place = new place(KnownPlaces.WHITEHOUSE);
}

@Test
public void test_whiteHouse_street(){
   assertEquals("1600 Pennsylvania Avenue", place.getAddress());
}

@Test
public void test_whiteHouse_city(){
   assertEquals("Washington", place.getCity());
}

@Test
public void test_whiteHouse_state(){
   assertEquals("DC", place.getState());
}
</code>```

However, if I'm testing a setter, the code might look like this:

```<code>@Test
public void test_place_setCity(){
   String newCity = "timbuktu";
   Place place = new Place();
   place.setCity(newCity);
   assertEquals(newCity, place.getCity());
}
</code>```

The test will run properly, but if there's a shared setup, I'm making assumptions about the initial state.  What would be the downside on running a check on the initial state something like:

```<code>@Test
public void test_place_setCity(){
   String newCity = "timbuktu";
   Place place = new Place();
   assertFalse(place.getCity().equals(newCity));
   place.setCity(newCity);
   assertEquals(newCity, place.getCity());
}
</code>```

This check would verify that the setter method actually changed something by verifying the initial state was different than the final state.  Otherwise, a change or malfunction in a constructor or setup method could cause the test to become ineffective.  Are there any downsides to violating the one assert per constraint rule in this way?


答:
I wouldn't call it a rule but rather a guideline from the past. The common misunderstanding relates to what "one assertion" really means. Unfortunately, some people tend to bend it towards "one assert method call" without really giving it any thought. This is to some extent understandable, after all one of the first guidelines related to unit testing you'll probably hear that "unit test should be atomic, small and test one thing".

However, one assertion is more about logical concept than number of method calls in test. In your example, if all the getters provide simple value that has little to no sense existing outside of its entity, then all 3 asserts relate to one logical concept - your entity. If the getter produces more complex value, it might be worth having its own test. It's always a judgement call.

The code in your example uses well known pattern called guard assertion, and it's nothing wrong with that. Keep in mind however, that guard assertion might be always replaced by extra unit test, as noted here.


问:
How do you safely work around broken code?
Once in a while, a co-worker will check-in bad code which blocks my application from initializing properly.

To get around this problem quickly, I comment out the offending code. I then forget to uncomment the offending code at the time of my check-in, so I want to prevent this from happening again.

Do you have any suggestions on how to:

Disable bad code that stop you from working

Prevent yourself from checking in unwanted changes?

I'm currently using Visual Studio as my IDE and TFS as my source code repo.

答:
This sounds like a internal process issue more than a check-in issue. You should work with the person to ensure that they are doing proper testing and debugging to ensure that the code works. If you have a group of testers, make sure he is sending them his changes to test, they are usually good at finding problems.

You could also be bringing these discussions up in meetings - "Hey, will your code changes affect our changes in any way?", "How will we integrate our changes together without issue once we both are done?".

These are core to working as a team.


答:
Do you have a trick to prevent yourself from checking in unwanted changes?

Before committing a file, get a diff of your current version to the parent and double-check each change to make sure they're what you intend to commit. This is also a good time to analyze your changes as to whether it is the best solution, whether it will be hard for future developers to maintain, etc.

When I'm at a point where I want to commit, I typically take a look at each modified file to verify changes as described above, and as I go along, decide which files to group together in a single commit. After I've gone over them all, I commit files as planned.

This process requires that you commit more often, but that's often a good thing.

Title: How do you safely work around broken code?

Body:
Once in a while, a co-worker will check-in bad code which blocks my application from initializing properly.

To get around this problem quickly, I comment out the offending code. I then forget to uncomment the offending code at the time of my check-in, so I want to prevent this from happening again.

Do you have any suggestions on how to:

Disable bad code that stop you from working

Prevent yourself from checking in unwanted changes?

I'm currently using Visual Studio as my IDE and TFS as my source code repo.


问:
How old is "too old"?
I've been told that to be taken seriously as a job applicant, I should drop years of relevant experience off my résumé, remove the year I got my degree, or both. Or not even bother applying, because no one wants to hire programmers older than them.1

Or that I should found a company, not because I want to, or because I have a product I care about, but because that way I can get a job if/when my company is acquired.

Or that I should focus more on management jobs (which I've successfully done in the past) because… well, they couldn't really explain this one, except the implication was that over a certain age you're a loser if you're still writing code. But I like writing code.

Have you seen this? Is this only a local (Northern California) issue?

If you've ever hired programmers:2

Of the résumés you've received, how old was the eldest applicant?

What was the age of the oldest person you've interviewed?

How old (when hired) was the oldest person you hired?

How old is "too old" to employed as a programmer?

1 I'm assuming all applicants have equivalent applicable experience. This isn't about someone with three decades of COBOL applying for a Java guru job.

2 Yes, I know that (at least in the US) you aren't supposed to ask how old an applicant is. In my experience, though, you can get a general idea from a résumé.

答:
I'm 52, and Technology Director of a company I co-founded 15 years ago, and this is a question close to my heart. I spend about 40% of my time coding, mainly developing existing and new products and I truly hope to be doing the same thing in 10 years time.

I'm intrigued by the notion that older programmers are uniquely hampered by irrelevant skillsets. I find that this is the problem with younger developers - if I want an Flash Programmer, or a Flex Programmer, that's easy. If I want one with proven enterprise database or network skills, or with a track record of commercial product development, that's much more difficult to find. Older programmers can talk more articulately about design choices and software lifecycle issues simply because they've had a lifetime of experience of successes - and failures.

The problem for older programmers is not that they are losing their intellectual capacity, but that they've been seduced by the notion that they should become 'managers'. In my opinion a good programmer with decades of experience can earn more developing software than by climbing some ill-defined management ladder,  provided they find (or start) an organisation which rewards innovation and ability.

In a world where millions of developers with the same skillsets are available via the internet, the idea that youth alone has value is simply dumb.

Title: How old is "too old"?


问:
DDD: Service or Repository
I am developing an app in DDD manner. And I have a little problem with it.

I have a Fare (airline fare) and FareRepository objects. And at some point I should load additional fare information (from a server, call server api) and setup this information to existing Fare.

I guess that I need to create an Application Service (FareAdditionalInformationService) that will deal with obtaining data from the server and than update existing Fare or put the business logic in Fare object. However, some people said me that it is necessary to use FareRepository for this problem.

I don't know wich place is better for my problem Service or Repository.

UPDATE:

After researching, I came to the conclusion, that the better place for fetching additional Fare information is a service like (AdditionalFareService).

The code would look something like this:

```<code>//create service for fetching fare information
AdditionalFareService service = new AdditionalFareService();
//get a fare by Id
Fare fare = fareRepository.GetById(myFareId);
//Obtain information from service
var fareInformation=service.getAdditionalInformation(fare)
//Add it to the fare.
fare.AddInformation(fareInformation);
//save it to the repository.
fareRepository.Save(fare);
</code>```

答:
I'm assuming that the FareInformation provides details about a given Fare (e.g. special terms and conditions, change fees, etc.)

You need a way to create and save a FareInformation in order to associate it with the Fare. In this case, I'd say provide methods on the Fare that does it for you.

The API would look something like this

```<code>//get a fare by Id
Fare fare = fareRepository.GetById(myFareId);
//Create a change fee object.
var fareInformation=new ChangeFee(new UsdCurrency(50.00d))
//Add it to the fare.
fare.AddInformation(fareInformation);
//save it to the repository.
fareRepository.Save(fare);
</code>```

Note that I'm sending a ChangeFee object and not a FareInformation object. FareInformation is a base class in a hierarchy. I'm relying on the O/RM to map the hierarchy to a database structure for me.

Title: DDD: Service or Repository

Body:
I'm assuming that the FareInformation provides details about a given Fare (e.g. special terms and conditions, change fees, etc.)

You need a way to create and save a FareInformation in order to associate it with the Fare. In this case, I'd say provide methods on the Fare that does it for you.

The API would look something like this

//get a fare by Id
Fare fare = fareRepository.GetById(myFareId);
//Create a change fee object.
var fareInformation=new ChangeFee(new UsdCurrency(50.00d))
//Add it to the fare.
fare.AddInformation(fareInformation);
//save it to the repository.
fareRepository.Save(fare);

Note that I'm sending a ChangeFee object and not a FareInformation object. FareInformation is a base class in a hierarchy. I'm relying on the O/RM to map the hierarchy to a database structure for me.


答:
You should consider using feature branches in your source repository.

Also consider a continuous integration server. It will help ensure that only compilable code is checked in to the source tree. Even better if it passes automatic unit tests.


答:
Bad code shouldn't be committed in the first place. Breaking the build isn't a nice thing to do when one works in a team, and different teams have different approaches to encourage the developers to check twice before committing the code.

If the code breaks the build, you shouldn't comment it. Either you see where the problem is, so you can easily solve it yourself, or you should discuss the issue directly with the person who committed bad code. Just committing the code will not make the problem disappear. It's like turning your back to a monster: you wouldn't see the monster any longer, but the beast is still here.

Also note that:

The bad code is already committed. If you don't want this code to be in the build, instead of commenting it, delete it. You can always recover the code from the version control; that's the point of having one.

The issue may come from a developer who usually use version control systems like Git. In those systems, one can commit as many times as he want, without affecting the work of other people. Once the code is checked for correctness, it is committed to the wild, affecting the whole team.

Developers who work this way are usually lost when it comes to older version control systems, like SVN. If they are committing their changes too often, they cannot check the code for correctness every time; at the same time, it's not very correct to force them to commit less frequently.


问:
Scuttlebutt Reconciliation in the paper “Efficient Reconciliation and Flow Control for Anti-Entropy Protocols”
I am reading the paper "Efficient Reconciliation and Flow Control for Anti-Entropy Protocols"! , I couldn't clearly understand Section 3.2 "Scuttlebutt Reconciliation". Here I extract out some sentences from the paper, which especially confuse me.

If gossip messages were unlimited in size, then the sets contains the exact differences,just like with precise reconciliation.

Scuttlebutt requires that if a certain delta (r; k; v; n) is omitted, then all the deltas with higher version numbers for the same r should be omitted as well.

Scuttlebutt satises the global invariant C(p;q) for any two
processes p and q:

答:
There's not really a question here, but I happen to have read that paper just now. I'll try to provide my interpretation.

This sentence states that Scuttlebut reconciliation will not differ from precise reconciliation if there was no maximum to the size of network messages. Obviously, there is; this is the whole point of coming up with a clever reconciliation mechanism.

This sentence states that there can be no gaps in the sequence of changes (deltas) that are part of a single Scuttlebut message. If a particular change is not transmitted in some message, then it is not allowed to include any change that is more recent that the omitted message. So in short: a message always contains a set of changes that are the oldest among changes not known to the peer that will receive the message.

The invariant ensures that for each key k in the set of state variables, participant q either has the current value of k present at participant p, or the version number (or timestamp) of the current value at p is higher than the maximum version number of all values at p that q knows about. All in all, this has to do with the absence of gaps again.

Writing this up has made things more clearer for myself, hope it helps you :)
(feel free to comment when things are still too fuzzy)


答:
As far as I know, developing your application in DDD manner you are working on Domain Model pattern (http://martinfowler.com/eaaCatalog/domainModel.html).

If it is your case, such logic should be encapsulated IN your domain object (Fare).
The Fare object itself should expose methods that work ON the domain object and manipulating its state accordingly.

Title: DDD: Service or Repository

Body:
I am developing an app in DDD manner. And I have a little problem with it.

I have a Fare (airline fare) and FareRepository objects. And at some point I should load additional fare information (from a server, call server api) and setup this information to existing Fare.

I guess that I need to create an Application Service (FareAdditionalInformationService) that will deal with obtaining data from the server and than update existing Fare or put the business logic in Fare object. However, some people said me that it is necessary to use FareRepository for this problem.

I don't know wich place is better for my problem Service or Repository.

UPDATE:

After researching, I came to the conclusion, that the better place for fetching additional Fare information is a service like (AdditionalFareService).

The code would look something like this:

```<code>//create service for fetching fare information
AdditionalFareService service = new AdditionalFareService();
//get a fare by Id
Fare fare = fareRepository.GetById(myFareId);
//Obtain information from service
var fareInformation=service.getAdditionalInformation(fare)
//Add it to the fare.
fare.AddInformation(fareInformation);
//save it to the repository.
fareRepository.Save(fare);
</code>```


问:
Why is it said that V-model introduces QA?
In several articles and books I learnt that "V-model introduced QA into SW development".

I would like to understand the point of such statement, as from my understanding, V model activities (verification and validation) cannot be considered as QA as both deal directly with product control, no matter if it's static (verification) or dynamic (validation).

I would agree that testing (say V&V) is a tool used by QA to measure the quality, but how does it assure it?

Examples in Google Books:

"Real-Time Systems Design and Analysis: Tools for the Practitioner"."..these QA activities form the heart of the V model..."

or

Iterative Software Engineering for Multiagent Systems: The MASSIVE..:
the V-Model adds explicit quality assurance mechanisms to the Waterfall model: verification is concerned...

答:
I'm not sure where you read that the v-model introduced QA into software development. That statement doesn't even make sense. What the v-model does is explicitly relate some of the different quality activities, such as acceptance testing, system testing, integration testing, and unit testing back to the upstream activities that they are connected to. Rather than "testing" being an afterthought after development and integration, quality activities are explicitly linked to up-front activities in the lifecycle. However, it also says nothing about a number of other quality activities - reviews and inspections, measurements and metrics, auditing, and reporting.

Software quality assurance is a set of activities that go into ensuring that the product being built maintains the desired level of quality by both monitoring the product as well as the processes used to produce that product. In order to monitor quality, you need to do what you are referring to as "quality control" activities - verification and validation testing - in order to obtain both quantitative and qualitative measures of process and product quality.

The assurance part comes in when this data is used to prevent problems by taking corrective action against problems, either by identifying problems early or by changing the processes to prevent problems from happening. This includes both the product and the process. For example, carrying out requirements reviews is a V&V activity, but by integrating a quality activity up front, you are being pro-active in preventing a defect from entering the product under construction. A robust quality assurance effort will also look at why defects are happening and attempt to correct them, using quality tools such as Pareto charting to identify the biggest causes of defects in work products and 5 Why Analysis to determine the root causes of them in order to apply corrective action. Beyond looking at problems, software quality assurance also addresses the things that are being done right, or the defects that are effectively finding and eliminating defects in work products or the system under development.

Another possible point of confusion might be in what organizations consider to be the role of a software quality assurance team. In my experiences, software quality assurance tends to focus more on the product quality than the process quality. At most, they might be responsible for gathering some metrics that can be used for process quality, but their primary responsibility is not on addressing how to build software, but answering the questions from V&V - was the right thing build and was the thing built right.


答:
To answer (1) how about:

```<code>#ifndef DODGY_CODE_I_WANT_TO_DISABLE
.
.
// the dodgy code
.
.
#endif
</code>```

This, obviously, is C syntax, but similar is no doubt available for whatever language you are using.

Never (and I mean NEVER) "comment out" code to disable it, as (a) this will get lost/forgotten about, and gets confused for genuine comments, and (b) comments within it might accidentally end the comment.

Body:
To answer (1) how about:

#ifndef DODGY_CODE_I_WANT_TO_DISABLE
.
.
// the dodgy code
.
.
#endif

This, obviously, is C syntax, but similar is no doubt available for whatever language you are using.

Never (and I mean NEVER) "comment out" code to disable it, as (a) this will get lost/forgotten about, and gets confused for genuine comments, and (b) comments within it might accidentally end the comment.


问:
Does the term "Learning Curve" include the knowing of the gotchas?
When you learn new technology you spend time understanding its concepts and tools.
But when technology meets real life strange and not pleasant things happen.
Reuqirements are often far from ideal and differ from 'classic' scenario.
And soon I find myself bending  the technology to my real needs. At this point I begin to know bugs of the system or that is is not so flexible as it seemed at the very begining.
And this 'fighting' with technology consumes a great part of the time while developing.
What is more depressing is that the bunch of such gotchas and workarounds are not concentrated at one place (book, site, etc.) And before you really confront it you cannot really ask the correct question because you do not even suspect the reason for the problem to occur (unknown-unknown).

So my question consiststs of three:

1) Do you really manage (and how) to predict possible future problems?

2) How much time do you spend for finding the workaround/fix/solution before you leave it and switch to other problems.

3) What are the criteria for you to think about yourself as experienced in the tecnology. Do you take these gotchas into account?

答:
The reason it's called a learning curve (as opposed to a learning slope) is that it starts out steeper and levels out but never truly becomes flat. There's always something you don't know. And there's always something that you don't know you don't know.

You learn from experience, and it's an unfortunate truism that you learn more from your mistakes than your successes.

To answer your specific questions:

Do you really manage (and how) to predict possible future problems?

To some extent. A lot of it comes from my own experiences and those of people I've worked with. But it's not entirely "I can't predict something unless I've seen the problem before." You start to get a spidey-sense for the areas where gotchas reside. I understand why you currently feel that there's no pattern to them, but over time you'll find that there is, in a lot of cases.

There are certain things that scream out "Here be dragons" without you really knowing what colour the dragons might be. But, in those cases, you can usually get that information from Google.

How much time do you spend for finding the workaround/fix/solution before you leave it and switch to other problems.

Depends again on that instinctive sense. I've run into a problem just this week that I never saw coming and never would have spent time looking for. I made a very obvious assumption that I think most people would make, and I'd make it again.

But there are certain areas (for example, anything to do with communications) that I don't go near without Googling for gotchas.

What are the criteria for you to think about yourself as experienced in the tecnology. Do you take these gotchas into account?

I think experience is relative. There is no "I am experienced in this technology," no matter how much we try to claim there is on a resume. I think it's all about whether you're more experienced in the areas of risk that you're facing than other people you're working with.

ie. How often do you spot those gotchas, before they become problems, compared to your colleagues?