Skip to content

Commit

Permalink
Updated to support Grails 2.3 and Scaffolding 2.0
Browse files Browse the repository at this point in the history
  • Loading branch information
robbugh committed Oct 14, 2013
1 parent c74677e commit b6a16a1
Show file tree
Hide file tree
Showing 10 changed files with 409 additions and 223 deletions.
7 changes: 4 additions & 3 deletions application.properties
@@ -1,4 +1,5 @@
#Grails Metadata file
#Sat Apr 06 13:47:56 BST 2013
app.grails.version=2.2.1
app.name=angular-scaffolding
#Mon Oct 14 03:48:27 CDT 2013
app.grails.version=2.3.0
app.name=angular-scaffolding
app.servlet.version=2.5
1 change: 1 addition & 0 deletions grails-app/conf/BuildConfig.groovy
Expand Up @@ -22,5 +22,6 @@ grails.project.dependency.resolution = {
build(':release:2.2.0', ':rest-client-builder:1.0.2') {
export = false
}
compile ':scaffolding:2.0.0'
}
}
24 changes: 24 additions & 0 deletions grails-app/conf/Config.groovy
Expand Up @@ -22,3 +22,27 @@ log4j = {

warn 'org.mortbay.log'
}

// Uncomment and edit the following lines to start using Grails encoding & escaping improvements

/* remove this line
// GSP settings
grails {
views {
gsp {
encoding = 'UTF-8'
htmlcodec = 'xml' // use xml escaping instead of HTML4 escaping
codecs {
expression = 'html' // escapes values inside null
scriptlet = 'none' // escapes output from scriptlets in GSPs
taglib = 'none' // escapes output from taglibs
staticparts = 'none' // escapes output from static template parts
}
}
// escapes all not-encoded output at final stage of outputting
filteringCodecForContentType {
//'text/html' = 'html'
}
}
}
remove this line */
115 changes: 4 additions & 111 deletions scripts/_NgGenerate.groovy
@@ -1,12 +1,7 @@
import grails.util.GrailsNameUtils
import org.codehaus.groovy.grails.commons.GrailsDomainClass
import org.springframework.core.io.FileSystemResource
import org.springframework.core.io.support.PathMatchingResourcePatternResolver
import org.springframework.util.Assert
import org.codehaus.groovy.grails.scaffolding.*

includeTargets << grailsScript("_GrailsCreateArtifacts")
includeTargets << grailsScript("_GrailsGenerate")
includeTargets << new File("scaffoldingPluginDir/scripts/_GrailsGenerate.groovy")
includeTargets << grailsScript("_GrailsBootstrap")

generateForName = null
Expand Down Expand Up @@ -37,7 +32,9 @@ target(generateForOne: 'Generates controllers and views for only one domain clas
}

def generateForDomainClass(domainClass) {
def templateGenerator = new AngularTemplateGenerator(classLoader)
def AngularTemplateGenerator = classLoader.loadClass('grails.plugin.angularscaffolding.AngularTemplateGenerator')
def templateGenerator = AngularTemplateGenerator.newInstance(classLoader)

templateGenerator.grailsApplication = grailsApp
templateGenerator.pluginManager = pluginManager
templateGenerator.event = event
Expand All @@ -53,107 +50,3 @@ def generateForDomainClass(domainClass) {
event 'GenerateControllerEnd', [domainClass.fullName]
}
}

/**
* Can't seem to load this if it's on the plugin source path so I've inlined it here
*/
class AngularTemplateGenerator extends DefaultGrailsTemplateGenerator {

def event

AngularTemplateGenerator(ClassLoader classLoader) {
super(classLoader)
}

def renderEditor = { property, prefix ->
def domainClass = property.domainClass
def cp
if (pluginManager?.hasGrailsPlugin('hibernate')) {
cp = domainClass.constrainedProperties[property.name]
}

if (!renderEditorTemplate) {
// create template once for performance
def templateText = getTemplateText('renderEditor.template')
renderEditorTemplate = engine.createTemplate(templateText)
}

def binding = [
pluginManager: pluginManager,
property: property,
domainClass: domainClass,
cp: cp,
domainInstance: getPropertyName(domainClass),
prefix: prefix
]
renderEditorTemplate.make(binding).toString()
}

@Override
void generateViews(GrailsDomainClass domainClass, String destdir) {
Assert.hasText destdir, 'Argument [destdir] not specified'

for (t in getTemplateNames()) {
event 'StatusUpdate', ["Generating $t for domain class ${domainClass.fullName}"]
generateView domainClass, t, new File(destdir).absolutePath
}
}

@Override
void generateView(GrailsDomainClass domainClass, String viewName, Writer out) {
def templateText = getTemplateText(viewName)

if (templateText) {

def t = engine.createTemplate(templateText)
def multiPart = domainClass.properties.find {it.type == ([] as Byte[]).class || it.type == ([] as byte[]).class}

boolean hasHibernate = pluginManager?.hasGrailsPlugin('hibernate')
def packageName = domainClass.packageName ? "<%@ page import=\"${domainClass.fullName}\" %>" : ""
def binding = [pluginManager: pluginManager,
packageName: packageName,
domainClass: domainClass,
multiPart: multiPart,
className: domainClass.shortName,
propertyName: getPropertyName(domainClass),
renderEditor: renderEditor,
comparator: hasHibernate ? DomainClassPropertyComparator : SimpleDomainClassPropertyComparator]

t.make(binding).writeTo(out)
}
}

@Override
void generateView(GrailsDomainClass domainClass, String viewName, String destDir) {
def suffix = viewName.find(/\.\w+$/)

def viewsDir = suffix == '.html' ? new File("$destDir/web-app/ng-templates/$domainClass.propertyName") : new File("$destDir/grails-app/views/$domainClass.propertyName")
if (!viewsDir.exists()) viewsDir.mkdirs()

def destFile = new File(viewsDir, "$viewName")
destFile.withWriter { Writer writer ->
generateView domainClass, viewName, writer
}
}

@Override
def getTemplateNames() {
def resources = []
def resolver = new PathMatchingResourcePatternResolver()
def templatesDirPath = "${basedir}/src/templates/scaffolding"
def templatesDir = new FileSystemResource(templatesDirPath)
if (templatesDir.exists()) {
try {
resources.addAll(resolver.getResources("file:$templatesDirPath/*.html").filename)
resources.addAll(resolver.getResources("file:$templatesDirPath/*.gsp").filename)
} catch (e) {
event 'StatusError', ['Error while loading views from grails-app scaffolding folder', e]
}
}

resources
}

private String getPropertyName(GrailsDomainClass domainClass) { "${domainClass.propertyName}${domainSuffix}" }

}
@@ -0,0 +1,112 @@
package grails.plugin.angularscaffolding

import org.springframework.util.Assert
import org.codehaus.groovy.grails.commons.GrailsDomainClass
import org.springframework.core.io.FileSystemResource
import org.springframework.core.io.support.PathMatchingResourcePatternResolver
import org.codehaus.groovy.grails.scaffolding.*

/**
* Can't seem to load this if it's on the plugin source path so I've inlined it here
*/
class AngularTemplateGenerator extends DefaultGrailsTemplateGenerator
{
def event

AngularTemplateGenerator(ClassLoader classLoader) {
super(classLoader)
}

def renderEditor = { property, prefix ->
def domainClass = property.domainClass
def cp
if (pluginManager?.hasGrailsPlugin('hibernate')) {
cp = domainClass.constrainedProperties[property.name]
}

if (!renderEditorTemplate) {
// create template once for performance
def templateText = getTemplateText('renderEditor.template')
renderEditorTemplate = engine.createTemplate(templateText)
}

def binding = [
pluginManager: pluginManager,
property: property,
domainClass: domainClass,
cp: cp,
domainInstance: getPropertyName(domainClass),
prefix: prefix
]
renderEditorTemplate.make(binding).toString()
}

@Override
void generateViews(GrailsDomainClass domainClass, String destdir) {
Assert.hasText destdir, 'Argument [destdir] not specified'

for (t in getTemplateNames()) {
event 'StatusUpdate', ["Generating $t for domain class ${domainClass.fullName}"]
generateView domainClass, t, new File(destdir).absolutePath
}
}

@Override
void generateView(GrailsDomainClass domainClass, String viewName, Writer out) {
def templateText = getTemplateText(viewName)

if (templateText) {

def t = engine.createTemplate(templateText)
def multiPart = domainClass.properties.find {it.type == ([] as Byte[]).class || it.type == ([] as byte[]).class}

boolean hasHibernate = pluginManager?.hasGrailsPlugin('hibernate')
def packageName = domainClass.packageName ? "<%@ page import=\"${domainClass.fullName}\" %>" : ""
def binding = [pluginManager: pluginManager,
packageName: packageName,
domainClass: domainClass,
multiPart: multiPart,
className: domainClass.shortName,
propertyName: getPropertyName(domainClass),
renderEditor: renderEditor,
comparator: hasHibernate ? DomainClassPropertyComparator : SimpleDomainClassPropertyComparator]

println "viewName: $viewName, domainClass: $domainClass, class: ${domainClass.class.name}"
t.make(binding).writeTo(out)
}
}

@Override
void generateView(GrailsDomainClass domainClass, String viewName, String destDir) {
def suffix = viewName.find(/\.\w+$/)

def viewsDir = suffix == '.html' ? new File("$destDir/web-app/ng-templates/$domainClass.propertyName") : new File("$destDir/grails-app/views/$domainClass.propertyName")
if (!viewsDir.exists()) viewsDir.mkdirs()

def destFile = new File(viewsDir, "$viewName")
destFile.withWriter { Writer writer ->
generateView domainClass, viewName, writer
}
}

@Override
protected Set<String> getTemplateNames() {
def resources = []
def resolver = new PathMatchingResourcePatternResolver()
def templatesDirPath = "${basedir}/src/templates/scaffolding"
def templatesDir = new FileSystemResource(templatesDirPath)
if (templatesDir.exists()) {
try {
resources.addAll(resolver.getResources("file:$templatesDirPath/*.html").filename)
resources.addAll(resolver.getResources("file:$templatesDirPath/*.gsp").filename)
} catch (e) {
event 'StatusError', ['Error while loading views from grails-app scaffolding folder', e]
}
}

resources as Set
}

protected String getPropertyName(GrailsDomainClass domainClass) { "${domainClass.propertyName}${domainSuffix}" }

}
2 changes: 2 additions & 0 deletions src/templates/common/sortable.html
@@ -0,0 +1,2 @@
<span data-ng-transclude></span>
<i data-ng-class="{'icon-sort-up': isSortedByAscending(), 'icon-sort-down': isSortedByDescending()}" data-ng-show="isSortedBy()"></i>
11 changes: 7 additions & 4 deletions src/templates/scaffolding/create.html
Expand Up @@ -6,10 +6,13 @@ <h1>Create ${className}</h1>
<form name="form" data-ng-submit="save(item)" class="form-horizontal">
<% excludedProps = Event.allEvents.toList() << 'version' << 'dateCreated' << 'lastUpdated'
persistentPropNames = domainClass.persistentProperties*.name
boolean hasHibernate = pluginManager?.hasGrailsPlugin('hibernate')
if (hasHibernate && org.codehaus.groovy.grails.orm.hibernate.cfg.GrailsDomainBinder.getMapping(domainClass)?.identity?.generator == 'assigned') {
persistentPropNames << domainClass.identifier.name
}
boolean hasHibernate = pluginManager?.hasGrailsPlugin('hibernate') || pluginManager?.hasGrailsPlugin('hibernate4')
if (hasHibernate) {
def GrailsDomainBinder = getClass().classLoader.loadClass('org.codehaus.groovy.grails.orm.hibernate.cfg.GrailsDomainBinder')
if (GrailsDomainBinder.newInstance().getMapping(domainClass)?.identity?.generator == 'assigned') {
persistentPropNames << domainClass.identifier.name
}
}
props = domainClass.properties.findAll { persistentPropNames.contains(it.name) && !excludedProps.contains(it.name) }
Collections.sort(props, comparator.constructors[0].newInstance([domainClass] as Object[]))
for (p in props) {
Expand Down
11 changes: 7 additions & 4 deletions src/templates/scaffolding/edit.html
Expand Up @@ -8,10 +8,13 @@ <h1>Edit ${className}</h1>
<input type="hidden" data-ng-model="item.version">
<% excludedProps = Event.allEvents.toList() << 'version' << 'dateCreated' << 'lastUpdated'
persistentPropNames = domainClass.persistentProperties*.name
boolean hasHibernate = pluginManager?.hasGrailsPlugin('hibernate')
if (hasHibernate && org.codehaus.groovy.grails.orm.hibernate.cfg.GrailsDomainBinder.getMapping(domainClass)?.identity?.generator == 'assigned') {
persistentPropNames << domainClass.identifier.name
}
boolean hasHibernate = pluginManager?.hasGrailsPlugin('hibernate') || pluginManager?.hasGrailsPlugin('hibernate4')
if (hasHibernate) {
def GrailsDomainBinder = getClass().classLoader.loadClass('org.codehaus.groovy.grails.orm.hibernate.cfg.GrailsDomainBinder')
if (GrailsDomainBinder.newInstance().getMapping(domainClass)?.identity?.generator == 'assigned') {
persistentPropNames << domainClass.identifier.name
}
}
props = domainClass.properties.findAll { persistentPropNames.contains(it.name) && !excludedProps.contains(it.name) }
Collections.sort(props, comparator.constructors[0].newInstance([domainClass] as Object[]))
for (p in props) {
Expand Down
7 changes: 4 additions & 3 deletions web-app/WEB-INF/applicationContext.xml
@@ -1,8 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

<bean id="grailsApplication" class="org.codehaus.groovy.grails.commons.GrailsApplicationFactoryBean">
<description>Grails application factory bean</description>
Expand Down Expand Up @@ -30,4 +29,6 @@ http://www.springframework.org/schema/beans http://www.springframework.org/schem
<value>utf-8</value>
</property>
</bean>

<bean id="conversionService" class="org.springframework.context.support.ConversionServiceFactoryBean" />
</beans>

0 comments on commit b6a16a1

Please sign in to comment.