Codex または Claude でインストール この Prompt をコピーして Codex、Claude、または他のアシスタントに貼り付けると、Skill ページを確認してインストールできます。
直接コマンドでは確認用 Prompt が省略されます。実行前にソースを確認してください。
npx skills add https://github.com/Objective-Arts/lens --skill javaコマンドは1行のまま表示されます。コピー前に横へスクロールして全体を確認してください。
ローカルで確認しますか?SkillsMP が現在取得できるファイルをダウンロードできます。
Audit a project against a canon's rules and checklist. Read-only — produces prioritized report without fixing. Works with any canon (nextjs, sql, typescript, etc.).
Lens home base - status, help, and setup
Plan and build a new feature with quality gates.
SKILL.md を表示中
SOC 職業分類に基づく
| name | java |
| description | Effective Java patterns |
| allowed-tools | [] |
Josh Bloch's core belief: APIs should be easy to use correctly and hard to use incorrectly. Every design decision should make the right thing easy and the wrong thing difficult or impossible.
"When in doubt, leave it out."
If you're unsure whether a feature, parameter, or method belongs, it probably doesn't. You can always add later. You can never remove without breaking clients.
Immutable objects are simple, thread-safe, and can be shared freely.
Make classes immutable unless there's a good reason not to:
Not this:
public class Period {
private Date start;
private Date end;
public void setStart(Date start) { this.start = start; }
public Date getStart() { return start; } // Leaks mutable reference
}
This:
public final class Period {
private final Date start;
private final Date end;
public Period(Date start, Date end) {
this.start = new Date(start.getTime()); // Defensive copy
this.end = new Date(end.getTime());
if (this.start.compareTo(this.end) > 0)
throw new IllegalArgumentException("start after end");
}
public Date getStart() { return new Date(start.getTime()); } // Defensive copy
}
Static factories have names, don't require new object creation, and can return subtypes.
Not this:
Boolean flag = new Boolean(true); // Always creates object
This:
Boolean flag = Boolean.valueOf(true); // Can return cached instance
Name conventions:
from - type conversion: Date.from(instant)of - aggregation: EnumSet.of(JACK, QUEEN, KING)valueOf - verbose alternative to ofgetInstance / instance - returns instance (may be cached)newInstance / create - guarantees new instancegetType / newType - factory in different classInheritance violates encapsulation. The subclass depends on implementation details of the superclass.
Not this:
public class InstrumentedHashSet<E> extends HashSet<E> {
private int addCount = 0;
@Override
public boolean add(E e) {
addCount++;
return super.add(e); // What if HashSet.addAll calls add()?
}
@Override
public boolean addAll(Collection<? extends E> c) {
addCount += c.size();
return super.addAll(c); // Double counting!
}
}
This (composition with forwarding):
public class InstrumentedSet<E> implements Set<E> {
private final Set<E> s;
private int addCount = 0;
public InstrumentedSet(Set<E> s) { this.s = s; }
public boolean add(E e) {
addCount++;
return s.add(e);
}
public boolean addAll(Collection<? extends E> c) {
addCount += c.size();
return s.addAll(c);
}
// ... delegate all other Set methods to s
}
If you allow inheritance, document precisely what subclasses can rely on. If you don't want to make that commitment, make the class final.
Refer to objects by their interfaces. This allows flexibility to change implementations.
Not this:
LinkedHashSet<String> names = new LinkedHashSet<>();
This:
Set<String> names = new LinkedHashSet<>();
Never force callers to write null checks for collections.
Not this:
public List<Item> getItems() {
if (items.isEmpty()) return null; // Forces null check
return items;
}
This:
public List<Item> getItems() {
return items.isEmpty()
? Collections.emptyList()
: new ArrayList<>(items);
}
Optionals are for return values that might legitimately be absent. Never use for fields, parameters, or collections.
Appropriate:
public Optional<Item> findById(long id) {
return Optional.ofNullable(cache.get(id));
}
Never:
// Don't do any of these
private Optional<Item> item; // Field
public void process(Optional<Item> item) { } // Parameter
public Optional<List<Item>> getItems() { } // Optional of collection
Detect errors as early as possible. Validate parameters at the start of methods.
Not this:
public void process(String input) {
// ... 50 lines of code ...
input.toLowerCase(); // NullPointerException here, far from cause
}
This:
public void process(String input) {
Objects.requireNonNull(input, "input must not be null");
if (input.isEmpty()) {
throw new IllegalArgumentException("input must not be empty");
}
// ... proceed with valid input ...
}
If you override equals, you must override hashCode. Objects that are equal must have equal hash codes.
The equals contract:
x.equals(x) is truex.equals(y) iff y.equals(x)x.equals(y) and y.equals(z), then x.equals(z)x.equals(null) is falseWhen constructors have many parameters (especially optional ones), use the Builder pattern.
NutritionFacts cocaCola = new NutritionFacts.Builder(240, 8)
.calories(100)
.sodium(35)
.carbohydrate(27)
.build();
Before committing any API or class design, ask:
Apply these checks:
Use a different skill when:
simplicity (Go Proverbs, small interfaces)design-patterns (23 patterns catalog)correctness (invariants, weakest preconditions)clarity (readability, naming)optimization (cache behavior, profiling)Bloch is the Java/Kotlin skill—use it for defensive API design and robust object-oriented code.
"APIs should be easy to use correctly and hard to use incorrectly." — Josh Bloch