博客

Automatically Adding a Private Constructor with Sensei

December 14, 2020
Alan Richardson

Automatically Adding a Private Constructor with Sensei


In a utility class, when the fields and methods are static,  there is no obvious reason why I would ever instantiate it.

e.g. UtilityClass utility = new UtilityClass();

The code below is a simple implementation of a Utility class.

public class UtilityClass {
    public static final Boolean ULTIMATE_TRUTH = true;
    public static boolean getTrue(){
        return ULTIMATE_TRUTH;
    }
}


This is the type of coding pattern that Static Analysis tools can pick up, but they often don't supply the ability to fix the issue.

I can use Sensei to identify the coding pattern, and automatically generate a private constructor to make it impossible for me to instantiate the class.

Searching for the Class

I will add a new recipe on the Utility class called:

  •  Static Classes: create private constructor.


General Settings For Static Classes


And initially, I'll create a simple matcher to search for a class.

search:

  class: {}


This will match any class, which is good enough to let me get started writing a Quick Fix. Once I have a Quick Fix that works, I'll refine the search to make it highlight when there is more likely to be a class that requires a private constructor.

Quick Fix

For the Quick Fix, I will want to generate a private constructor.

In the example class this would look like:

   private UtilityClass(){}

To add the above code to my class, my Quick Fix will add a Method, and the name of the method will be a Mustache template that uses the name of the class.

availableFixes:

- name: "add private constructor"
  actions:
  - addMethod:
      method: "private {{{ name }}}(){}"


In the GUI Editor, I use the Show Variables to create the Mustache template and then edit the field to add the private modifier, brackets, and braces to make it syntactically correct.

Add Private Constructor

This would now allow me to add a private constructor to any class.

The QuickFix preview helps me because I can see the generated code as I write the Mustache template.

Utility Class Add Private Constructor

Now that I know I can fix the problem. I'll refine the search conditions to show the recipe when it is most appropriate.

Search for Missing Constructors

Ideally, I don't want to create a recipe that flags an error against every class. So I'll add some additional conditions in the search so that we only match on classes that do not have a constructor.

search:

  class:
    without:
      child:
        method:
          constructor: true


The YAML is slightly different from the GUI.

In the GUI I configure it to look for a class without a child method which is a constructor 'yes'. We use 'yes' in the GUI instead of 'true' to make the GUI a little more human friendly.


Search for class in code


This recipe will now only reveal itself for any class without a constructor.

Narrow Search for Likely Culprits

So I might want to go further and look for the presence of static methods or fields.

I look for any class without a constructor and which has either all public static fields or all public static methods.

search:

  class:
    with:
      anyOf:
      - child:
          method:
            allOf:
            - modifier: "public"
            - modifier: "static"
      - child:
          field:
            allOf:
            - modifier: "static"
            - modifier: "public"
    without:
      child:
        method:
          constructor: true


Since Sensei is used to help me, as a  programmer, in the IDE, rather than to statically analyze the code and report all errors, this filter is good enough to rule out most classes in my code base where I might have a good reason to have a default public constructor.

In some projects, this might be a step too far because the utility classes could have private methods, so I might choose to look for the presence of 'any' public static methods, rather than 'all'.

       - child:
           field:
              anyOf:
                - modifier: "static"
                - modifier: "public"


Hints

Sensei is not designed to replace a Static Analysis tool. Sensei can augment a Static Analysis tool for common issues associated with your coding process, or technology. By replicating enough of the matching to highlight an issue, and supporting the development process by generating the QuickFix code.

What I'm trying to do is create a simple enough recipe that includes all the situations I need it, but filter it so that it doesn't get suggested in every class.

When working on recipes I try to de-risk them, in this case, I wasn't sure if I could create the private constructor so I created the QuickFix first. Then refactored the search conditions to make them more specific.

Sometimes when working on recipes I'm not sure how to perform the search, so I work on that first.

I find recipes easier to create when I build them incrementally, switching between refactoring of the QuickFix and the search.

---


You can install Sensei from within IntelliJ using "Preferences \ Plugins" (Mac) or "Settings \ Plugins" (Windows)  then just search for "sensei secure code"


The source code and recipes for this can be found in the `sensei-blog-examples` repository in the Secure Code Warrior GitHub account, in the `pojoexamples` module.

https://github.com/securecodewarrior/sensei-blog-examples

‍

标语

在 AI 驱动的开发成果发布前实现有效治理

评估 AI 辅助风险,在提交代码时强制执行安全编码策略,并加速整个软件开发生命周期的安全交付。

预约演示
资源库

探索更多博客

获取有关安全编码、人工智能治理和软件风险管理的专家内容。

浏览全部
案例研究
筛选标签
这是 div 块中的一段文本。

Supercharged Security Awareness: How Tournaments are Inspiring Developers at Erste Group

Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse varius enim in eros elementum tristique. Duis cursus, mi quis viverra ornare, eros dolor interdum nulla, ut commodo diam libero vitae erat. Aenean faucibus nibh et justo cursus id rutrum lorem imperdiet. Nunc ut sem vitae risus tristique posuere.

了解更多
案例研究
筛选标签
这是 div 块中的一段文本。

Security as culture: How Blue Prism cultivates world-class secure developers

Learn how Blue Prism, the global leader in intelligent automation for the enterprise, used Secure Code Warrior's agile learning platform to create a security-first culture with their developers, achieve their business goals, and ship secure code at speed

了解更多
案例研究
筛选标签
这是 div 块中的一段文本。

统一的安全文化:Sage 如何打造其安全倡导者项目

了解 Sage 如何通过灵活且以关系为导向的方法提升安全性,成功培养了 200 多名安全倡导者,并实现了显著的风险降低。

了解更多
博客
筛选标签
这是 div 块中的一段文本。

2026年网络安全意识月:理解人工智能安全对企业防御至关重要

目前,大多数顶级人工智能公司已公开呼吁全球放缓人工智能的发展速度,以便安全防护措施能够跟上步伐。然而事实是,严重的安全问题已经显现。随着人工智能实施带来的经济成本和风险不断累积,无数安全领导者和高管团队正处于紧迫的境地。

了解更多
博客
筛选标签
这是 div 块中的一段文本。

赋能要素 8:打造项目品牌

成功的安全编码项目不仅需要优质的内容。赋能要素 8 展示了如何通过品牌化将参与过程转变为一种令人向往、以地位为驱动的体验。

了解更多
博客
筛选标签
这是 div 块中的一段文本。

每一位员工现在都处于 AI 网络安全的最前线

企业技术格局正以一种鲜有人预料到的速度发生剧变,直到为时已晚。我们已正式跨越了从人工编写代码和基础辅助编程,进入“智能体开发生命周期”(ADLC)的时代。虽然自主 AI 智能体有望在多个职能领域实现前所未有的效率,但它们也带来了全新的安全和监管风险。

了解更多

在产品发布前确保 AI 驱动的开发安全

洞察开发风险,执行安全策略,并在整个软件开发生命周期中预防漏洞。

预约演示
未找到相关项目。