Skip to content

Commit

Permalink
Merge pull request #203 from grails/commands/create-interceptor
Browse files Browse the repository at this point in the history
Add command create-interceptor
  • Loading branch information
puneetbehl authored Sep 25, 2023
2 parents 1fdad47 + b2e50fa commit fc1c9ad
Show file tree
Hide file tree
Showing 5 changed files with 290 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
/*
* Copyright 2017-2020 original authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.grails.forge.cli.command;

import io.micronaut.context.annotation.Parameter;
import io.micronaut.core.annotation.ReflectiveAccess;
import io.micronaut.core.util.functional.ThrowingSupplier;
import jakarta.inject.Inject;
import org.grails.forge.application.Project;
import org.grails.forge.cli.CodeGenConfig;
import org.grails.forge.cli.command.templates.interceptor;
import org.grails.forge.cli.command.templates.interceptorSpec;
import org.grails.forge.io.ConsoleOutput;
import org.grails.forge.io.OutputHandler;
import org.grails.forge.template.RenderResult;
import org.grails.forge.template.RockerTemplate;
import org.grails.forge.template.TemplateRenderer;
import picocli.CommandLine;

import java.io.IOException;

@CommandLine.Command(name = CreateInterceptorCommand.NAME, description = "Creates a Interceptor Class")
public class CreateInterceptorCommand extends CodeGenCommand {

public static final String NAME = "create-interceptor";

@ReflectiveAccess
@CommandLine.Parameters(paramLabel = "INTERCEPTOR-NAME", description = "The name of the interceptor to create")
String interceptorName;

@Inject
public CreateInterceptorCommand(@Parameter CodeGenConfig config) {
super(config);
}

public CreateInterceptorCommand(CodeGenConfig config,
ThrowingSupplier<OutputHandler, IOException> outputHandlerSupplier,
ConsoleOutput consoleOutput) {
super(config, outputHandlerSupplier, consoleOutput);
}

@Override
public boolean applies() {
return true;
}

@Override
public Integer call() throws Exception {
final Project project = getProject(interceptorName);
final TemplateRenderer templateRenderer = getTemplateRenderer(project);
final RenderResult renderResult = templateRenderer.render(new RockerTemplate("grails-app/controllers/{packagePath}/{className}Interceptor.groovy", interceptor.template(project)), overwrite);
final RenderResult specRenderResult = templateRenderer.render(new RockerTemplate("src/test/groovy/{packagePath}/{className}InterceptorSpec.groovy", interceptorSpec.template(project)), overwrite);
if (renderResult != null && specRenderResult != null) {
logRenderResult(renderResult);
logRenderResult(specRenderResult);
}

return 0;
}

private void logRenderResult(RenderResult result) throws Exception {
if (result != null) {
if (result.isSuccess()) {
out("@|blue ||@ Rendered interceptor class to " + result.getPath());
} else if (result.isSkipped()) {
warning("Rendering skipped for " + result.getPath() + " because it already exists. Run again with -f to overwrite.");
} else if (result.getError() != null) {
throw result.getError();
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
@import org.grails.forge.application.Project

@args (
Project project
)

@if(project.getPackageName() != null) {
package @project.getPackageName()

}

class @project.getClassName()Interceptor {

boolean before() { true }

boolean after() { true }

void afterView() {
// no-op
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
@import org.grails.forge.application.Project

@args (
Project project
)

@if(project.getPackageName() != null) {
package @project.getPackageName()

}

import grails.testing.web.interceptor.InterceptorUnitTest
import spock.lang.Specification

class @project.getClassName()InterceptorSpec extends Specification implements InterceptorUnitTest<@project.getClassName()Interceptor> {

void "test interceptor matching"() {
when:
withRequest(controller: "@project.getClassName().toLowerCase()")

then:
interceptor.doesMatch()
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
package org.grails.forge.cli.command

import io.micronaut.context.ApplicationContext
import org.grails.forge.application.ApplicationType
import org.grails.forge.cli.CodeGenConfig
import org.grails.forge.cli.CommandFixture
import org.grails.forge.cli.CommandSpec
import org.grails.forge.io.ConsoleOutput
import spock.lang.AutoCleanup
import spock.lang.Shared

class CreateInterceptorCommandSpec extends CommandSpec implements CommandFixture {

@Shared
@AutoCleanup
ApplicationContext beanContext = ApplicationContext.run()


void "test creating a service"() {

setup:
generateProject(ApplicationType.WEB)
CodeGenConfig codeGenConfig = CodeGenConfig.load(beanContext, dir, ConsoleOutput.NOOP)
ConsoleOutput consoleOutput = Mock(ConsoleOutput)
CreateInterceptorCommand command = new CreateInterceptorCommand(codeGenConfig, getOutputHandler(consoleOutput), consoleOutput)
command.interceptorName = "test"

when:
Integer exitCode = command.call()
File output = new File(dir, "grails-app/controllers/example/grails/TestInterceptor.groovy")
File specOutput = new File(dir, "src/test/groovy/example/grails/TestInterceptorSpec.groovy")

then:
exitCode == 0
output.exists()
specOutput.exists()
2 * consoleOutput.out({ it.contains("Rendered interceptor") })
}

void "test app with interceptor"() {
setup:
generateProject(ApplicationType.WEB)
CodeGenConfig codeGenConfig = CodeGenConfig.load(beanContext, dir, ConsoleOutput.NOOP)
ConsoleOutput consoleOutput = Mock(ConsoleOutput)
CreateInterceptorCommand command = new CreateInterceptorCommand(codeGenConfig, getOutputHandler(consoleOutput), consoleOutput)

new File(dir, "grails-app/controllers/example/grails/TestController.groovy").text = '''package example.grails
class TestController {
def index() {
render request.getAttribute('foo')
}
}'''


when:
command.interceptorName = 'test'
Integer exitCode = command.call()
executeGradleCommand("test")

then:
exitCode == 0
testOutputContains("BUILD SUCCESSFUL")

when:
new File(dir, "src/test/groovy/example/grails/TestInterceptorSpec.groovy").text = '''package example.grails
import grails.testing.web.interceptor.InterceptorUnitTest
import spock.lang.Specification
class TestInterceptorSpec extends Specification implements InterceptorUnitTest<TestInterceptor> {
void "test interceptor matching"() {
when:
withRequest(controller: "test")
then:
interceptor.doesMatch()
when:
withRequest(controller: "person")
then:
!interceptor.doesMatch()
}
void "test controller execution with interceptors"() {
given:
def controller = (TestController)mockController(TestController)
when:
withInterceptors([controller: "test"]) {
controller.renderAttribute()
}
then:
response.text == "Foo is Bar"
}
}'''
executeGradleCommand("test")

then:
testOutputContains("TestInterceptorSpec > test controller execution with interceptors FAILED")

when:
new File(dir, "grails-app/controllers/example/grails/TestInterceptor.groovy").text = '''package example.grails
class TestInterceptor {
TestInterceptor() {
match(controller: "test")
}
boolean before() {
request.setAttribute('foo', 'Foo is Bar')
true
}
}'''

executeGradleCommand("test")

then:
testOutputContains("BUILD SUCCESSFUL")
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
package org.grails.forge.cli.command

import io.micronaut.configuration.picocli.PicocliRunner
import org.grails.forge.cli.CodeGenConfig
import org.grails.forge.utils.CommandSpec
import spock.lang.Ignore

class CreateInterceptorSpec extends CommandSpec {

@Ignore
void "test create-interceptor command"() {
when:
generateProjectWithDefaults()
applicationContext.createBean(CodeGenConfig.class, new CodeGenConfig())

then:
applicationContext.getBean(CodeGenConfig.class)

when:
PicocliRunner.run(CreateInterceptorCommand.class, applicationContext, "test")

then:
new File(dir, "grails-app/controllers/example/grails/TestInterceptor.groovy").exists()
new File(dir, "src/tests/example/grails/TestInterceptorSpec.groovy").exists()

}

@Override
String getTempDirectoryPrefix() {
return "test-app"
}
}

0 comments on commit fc1c9ad

Please sign in to comment.