sonar-openedge icon indicating copy to clipboard operation
sonar-openedge copied to clipboard

How to find all "define input parameter anyname as memptr"

Open jurjendijkstra opened this issue 4 years ago • 16 comments

I currently have a reason to find all occurences of the pattern "define input parameter * as memptr *." Because I have to look at them one by one and decide if I must refactor them to OUTPUT or INPUT-OUTPUT or leave as is.

What is the best way to do that? Using one of the template rules, like "Custom Groovy rule" or "Custom XREF rule". (Or maybe grep)

Anyone here willing to give me a working example? Please?

jurjendijkstra avatar Jul 29 '21 10:07 jurjendijkstra

The custom Groovy rule is the best way if you don't want to create a full plugin. Pseudo-code is:

for (TreeParserSymbolScope scope : unit.getRootSymbolScope().getChildScopesDeep()) {
  for (Parameter p : scope.getRoutine().getParameters()) {
    if (p.getDirectionNode() == ABLNodeType.INPUT) && (p.getSymbol().getDatatype() == DataType.MEMPTR)
      reportIssue(...)
  }
}

I had some time ago a Docker image to quickly test custom Groovy rules, I'll try to make it available next week.

gquerret avatar Jul 29 '21 11:07 gquerret

Awesome, thanks! I have time to wait for the Docker image.

jurjendijkstra avatar Jul 29 '21 11:07 jurjendijkstra

Not a Docker image, but a standalone JAR file: https://dl.rssw.eu/standalone-groovy-rule.jar

Example usage:

java -jar standalone-groovy-rule.jar --databases dump/sp2k.df,dump/empty.df:newdb --aliases sp2k,foobar;newdb,db2 --propath src/classes,src/procedures,src/tests --charset utf-8 --groovy file.groovy --input src/procedures/sample/test1.p

Source code: https://github.com/Riverside-Software/standalone-groovy-rule

gquerret avatar Jul 30 '21 14:07 gquerret

Sorry I don't know how to get it to work. The example with standalone-groovy-ruile.jar keeps saying nothing but Error: Could not find or load main class eu.rssw.sonar.GroovyRule. I have downloaded sonar-openedge-plugin-2.14.0.jar and sonar-plugin-api-7.9.4 to the current directory and all sonar extensions, but the error remains.

So then I thought, I will just enter the groovy script it in Sonarqube, because Sonarqube will have all dependencies. But the pseudo code is indeed psudo code, it does not run in Sonarqube. TreeParserSymbolScope and Parameter classes are unable to resolve.

I have searched the internet for an example of a working groovy custom rule but did not find any and also did not find a help/manual/webpage of which classes, methods or attributes might work in the groovy rule, so I don't know what to try or where to begin. Where should I look?

Custom groovy rules would be great, but I am stuck here.

jurjendijkstra avatar Aug 03 '21 08:08 jurjendijkstra

Sorry for the delay 😢 I'll provide more detailed instructions today.

gquerret avatar Aug 06 '21 07:08 gquerret

The example with standalone-groovy-ruile.jar keeps saying nothing but Error: Could not find or load main class eu.rssw.sonar.GroovyRule.

The JAR file has been updated on the server, please download again.

A sample rule was posted in a comment some time ago: https://github.com/Riverside-Software/sonar-openedge/issues/702#issuecomment-525265601 This is the very basic structure of any Groovy rule. And it assumes that you know how to develop in Java (at least, Groovy is very similar).

The Proparse API is visible from the source code (just git clone this repo), and Javadoc is published on Maven Central. Or directly here.

JPNode class with various query() methods is the main entry point to parse the source code. You can use it from unit.getTopNode().query(...). Another entry point is through the SymbolScope object: unit.getRootScope() where you'll have access to the various routines, and in turn to the parameter. The parameter is in turn linked to the JPNode object where it is defined. I'll let you play with that !

gquerret avatar Aug 06 '21 07:08 gquerret

I just tried to setup the standalone-groovy-rule.jar to play around with groovy rule develpment but it doesn't seem to work. Am i missing something? My groovy rule is the example from the template.

java -jar standalone-groovy-rule.jar --databases issdata.df:issdata --propath C:\Users\doa\Desktop\Groovy --charset utf-8 --groovy C:\Users\doa\Desktop\Groovy\GroovyRule.groovy --input C:\Users\doa\Desktop\Groovy\Test.p
Setting Proparse session with propath: C:\Users\doa\Desktop\Groovy - Charset: utf-8
Reading issdata schema from issdata.df
Parsing C:\Users\doa\Desktop\Groovy\Test.p
Reading Groovy script from C:\Users\doa\Desktop\Groovy\GroovyRule.groovy
Exception in thread "main" org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed:
C:\Users\doa\Desktop\Groovy\GroovyRule.groovy: 1: unable to resolve class eu.rssw.antlr.proparse.checks.GroovyTemplate.RuleLink
 @ line 1, column 1.
   import eu.rssw.antlr.proparse.checks.GroovyTemplate.RuleLink;
   ^

1 error

        at org.codehaus.groovy.control.ErrorCollector.failIfErrors(ErrorCollector.java:295)
        at org.codehaus.groovy.control.CompilationUnit$ISourceUnitOperation.doPhaseOperation(CompilationUnit.java:914)
        at org.codehaus.groovy.control.CompilationUnit.compile(CompilationUnit.java:627)
        at groovy.lang.GroovyClassLoader.doParseClass(GroovyClassLoader.java:389)
        at groovy.lang.GroovyClassLoader.lambda$parseClass$3(GroovyClassLoader.java:332)
        at org.codehaus.groovy.runtime.memoize.StampedCommonCache.compute(StampedCommonCache.java:163)
        at org.codehaus.groovy.runtime.memoize.StampedCommonCache.getAndPut(StampedCommonCache.java:154)
        at groovy.lang.GroovyClassLoader.parseClass(GroovyClassLoader.java:330)
        at groovy.lang.GroovyShell.parseClass(GroovyShell.java:526)
        at groovy.lang.GroovyShell.parse(GroovyShell.java:538)
        at groovy.lang.GroovyShell.parse(GroovyShell.java:547)
        at eu.rssw.sonar.GroovyRule.execute(GroovyRule.java:87)
        at eu.rssw.sonar.GroovyRule.main(GroovyRule.java:103)

movedoa avatar May 19 '22 09:05 movedoa

The RuleLink class is nested in GroovyRule (a modified version of GroovyTemplate) , so the import statement is different in this case ; it should be:

import eu.rssw.sonar.GroovyRule.RuleLink;

gquerret avatar May 19 '22 10:05 gquerret

Works now, thx.

But I have another question. In https://github.com/Riverside-Software/sonar-openedge/issues/702#issuecomment-539646226 yout told me that it is possible to access comments.

What i try i do is check our method header doc comments (For example, all parameters should be there). I already have the METHOD node and i see that the comments before are in the hiddenTokens array but i'm not sure if this is the right approach. Basically i need the first Comment before my METHOD node.

movedoa avatar May 19 '22 11:05 movedoa

You're right, comments are stored as hidden tokens (as a linked list) before the METHOD node. Note that whitespaces are on the same channel.

gquerret avatar May 19 '22 11:05 gquerret

Ok so i guess i have to find the first comment before my Method with the start and end positions?

movedoa avatar May 19 '22 12:05 movedoa

Token.getNodeType() will tell you if it's a comment or whitespace, then Token.getText() will give you the content

gquerret avatar May 19 '22 12:05 gquerret

Well....my groovy rule now works locally but i cant put it into sonar because its too long. Is there a way to bypass this limit?

grafik

movedoa avatar May 19 '22 15:05 movedoa

The value (in the DB) seems to be limited to 4000 characters. Is your code longer than that ?

gquerret avatar May 19 '22 21:05 gquerret

Yes it is. Considering the imports that i need are already 400 chars long, 4k seems way to tight. My rule currently sits at around 9K chars, i could surely trim it down some but not to 4k.

movedoa avatar May 20 '22 07:05 movedoa

Increasing the column size is not recommended by SonarSource, so your best option is to create a rules plugin. You can clone this plugin: https://github.com/riverside-Software/rules-plugin-template Presentation on this topic : https://www.pugchallenge.eu/docs/default-source/presentations-2018/custom-rules-development-with-sonarqube.pdf

The code that you've written can almost be copy / pasted.

gquerret avatar May 23 '22 07:05 gquerret