I am trying to execute following code but I am getting null pointer exception.
<property name="from" value="from"/>
<property name="to" value="to"/>
<taskdef name="groovy"
classname="org.codehaus.groovy.ant.Groovy"
classpath="G:\Tibco_Training\groovy-binary-1.8.5\groovy-all-1.6.5.jar" />
<taskdef resource="net/sf/antcontrib/antlib.xml"/>
<groovy>
class MoveDir extends org.apache.tools.ant.Task {
//def from = 'from'
//def to = 'to'
public void execute() {
new File(properties.from).eachFileMatch ~/.*/, { file ->
file.renameTo(new File(properties.to , file.getName()))
println "Moving file: $file.name from: " + from + " to: " + to }
}
}
project.addTaskDefinition('movedir', MoveDir)
</groovy>
<movedir />
If I don't use ant properties in groovy then the code works fine, but when I use ant properties for specifying directories, then it give null pointer exception. Am I passing wrong values or wrong syntax is the cause.
Wrong syntax, you have to use properties.'to' and properties.'from'
Related
I have a class OrderEntryData and inside I have an attribute which is a list of configurationInfoData (List< ConfigurationInfoData >) and inside this ConfigurationInfoData an attribute of Type Object (Object value).
This value will be sometime a date , a string or a customClass.
I am using Orika for the webServices and I am trying to settle the OrderEntryDTO class.
File : customcommerceWebServices-beans.xml
<bean class="de.hybris.platform.commercewebservicescommons.dto.order.ConfigurationInfoWsDTO">
<property name="label" type="java.lang.String" />
<property name="value" type="java.lang.Object" />
</bean>
<bean class="de.hybris.platform.commercewebservicescommons.dto.order.OrderEntryWsDTO">
<property name="configurationInfos" type="java.util.List<de.hybris.platform.commercewebservicescommons.dto.order.ConfigurationInfoWsDTO>" />
<property name="orderCode" type="java.lang.String" />
</bean>
I am testing with an Object which is an instance of AddressData.
Cause the Mapping/Conversion of the address object is working well
AddressData -> AddressDTO
the problem is (I think) Orika does not recognize the instance of the object (Object source) or the destination class (Object Target).
In the response I should have a AddressWsDTO but I get :
"de.hybris.platform.cmssmarteditwebservices.dto.AbstractPageWsDTO#54330c75"
I tried to implement a converter cause I was thinking maybe Orika don't Know how to convert an object to an AddressData (not working).
#WsDTOMapping
public class ScalpAddressConverter extends BidirectionalConverter<AddressData, Object> {
#Override
public Object convertTo(AddressData addressData, Type<Object> type, MappingContext mappingContext) {
return (Object) addressData;
}
#Override
public AddressData convertFrom(Object o, Type<AddressData> type, MappingContext mappingContext) {
return (AddressData) o;
}
}
In short I am not able to make a computation based on a property within my build file.
Let's say I have:
<property name="basedir" value="${project.basedir}" /> <--Current value 73
How can I know the previous 3 builds (72,71 and 70) OR how can I compute these values(based on the basedir property)?
I have tried (ignore the addition):
<property name="basedir" value="${project.basedir}+1" /> <--But it concats the value: 73+1
<property name="basedir" value="${project.basedir+1}" /> <--But it is just wrong: build_${env.BUILD_NUMBER+1}
Scenario: Remove old releases (keep some releases in case of a rollback)
P.S: The duplicate link is invalid because this is a deployment via PHING not ANT
You could use an adhoc-task for this:
<?xml version="1.0"?>
<project default="main" phingVersion="2.11.0">
<property name="basedir" value = "73"/>
<adhoc-task name="increment"><![CDATA[
class increment extends Task {
private $value;
function setvalue($value) {
$this->value = $value;
}
function setProperty($property) {
$this->property = $property;
}
function main() {
$this->project->setProperty($this->property, ((int) $this->value + 1));
}
}
]]></adhoc-task>
<target name="main">
<echo>${basedir}</echo>
<increment value="${basedir}" property="basedir"/>
<echo>${basedir}</echo>
</target>
</project>
I would like to know how to pass groovy script variables(here: compName, compPath) to the ant target (here : build.application)
I would like to make the values of compName and compPath available to all ant targets in this build.xml
<target name="xmlreader" description="Clean deployment directory">
<groovy>
import javax.xml.xpath.*
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
def ant = new AntBuilder()
File buildfile = new File("d:/Users/sk/workspace/build.xml")
fileContent = buildfile.getText()
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
Document doc = builder.parse(buildfile);
XPathFactory xPathfactory = XPathFactory.newInstance();
XPath xpath = xPathfactory.newXPath();
XPathExpression expr = xpath.compile("BuildConfig/Applications/ApplicationConfig");
NodeList nl = (NodeList) expr.evaluate(doc, XPathConstants.NODESET);
for (int i = 0; i < nl.getLength() ; i++) {
String compName = (String)nl.item(i).getElementsByTagName("Name").item(0).getChildNodes().item(0).getNodeValue();
String compPath = (String)nl.item(i).getElementsByTagName("SVN_Path").item(0).getChildNodes().item(0).getNodeValue();
ant.echo "${compName}"
ant.echo "${compPath}"
ant.ant( antfile: 'build.xml' ){
target(name: 'build.application')
}
}
</groovy>
</target>
To answer your direct question, the ant task accepts property children to set properties in the new project used by the target you're calling:
ant.ant( antfile: 'build.xml', target: 'build.application') {
property(name:'compName', value:compName)
property(name:'compPath', value:compPath)
}
But you could also consider xmltask, whose "call" function can achieve the same thing without all the Groovy code.
<xmltask source="d:/Users/sk/workspace/build.xml">
<call path="BuildConfig/Applications/ApplicationConfig" target="build.application">
<param name="compName" path="Name" />
<param name="compPath" path="SVN_Path" />
</call>
</xmltask>
I have input complex big XML files for the Mule flow.
File end point-> Byte Array to String -> Splitter -> ....
I have got org.xml.sax.SAXParseException: Content is not allowed in prolog when I try to process input files by using Splitter component. When I create new XML file and copy content of original file to the file, input files are processed.
I delete BOM marker when I create new file. Original file has EF BB BF since the beginning of the file, local file has not.
Mule config:
<?xml version="1.0" encoding="UTF-8"?>
<mule xmlns:tracking="http://www.mulesoft.org/schema/mule/ee/tracking"
xmlns:mulexml="http://www.mulesoft.org/schema/mule/xml"
xmlns:doc="http://www.mulesoft.org/schema/mule/documentation"
xmlns:spring="http://www.springframework.org/schema/beans" version="EE-3.4.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.mulesoft.org/schema/mule/file
http://www.mulesoft.org/schema/mule/file/current/mule-file.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans
current.xsd
http://www.mulesoft.org/schema/mule/core http://www.mulesoft.org/schema/mule/core/current/mule.xsd
http://www.mulesoft.org/schema/mule/xml http://www.mulesoft.org/schema/mule/xml/current/mule-xml.xsd
http://www.mulesoft.org/schema/mule/ee/tracking
http://www.mulesoft.org/schema/mule/ee/tracking/current/mule-tracking-ee.xsd">
<mulexml:dom-to-xml-transformer name="domToXml"/>
<flow name="SplitterFlow1" doc:name="SplitterFlow1">
<file:inbound-endpoint path="D:\WORK\Input"
moveToDirectory="D:\WORK\Output"
responseTimeout="10000" doc:name="File" fileAge="200" encoding="UTF-8"/>
<byte-array-to-string-transformer doc:name="Byte Array to String" />
<splitter evaluator="xpath" expression="/Invoices/invoice"
doc:name="Splitter"/>
<transformer ref="domToXml" doc:name="Transformer Reference"/>
<tracking:custom-event event-name="Invoice ID" doc:name="Custom Business event">
</tracking:custom-event>
<logger level="INFO" doc:name="Logger"/>
<file:outbound-endpoint path="D:\WORK\Output"
outputPattern="#[function:dateStamp:dd-MM-yyyy-HH.mm.ss]-#[header:OUTBOUND:MULE_CORRELATION_SEQUENCE]"
responseTimeout="10000" doc:name="File"></file:outbound-endpoint>
</flow>
</mule>
Please advise me how I can do it in the Mule flow. Thank you in advance.
It's a pretty old post but here is my contribution.
Additionaly to the Java transformer approach suggested by #alexander-shapkin, I strongly recommend that you use Apache Commons' org.apache.commons.io.BOMInputStream to handle BOM marker out-of-the-box. The code would look something like below:
import java.io.InputStream;
import org.apache.commons.io.ByteOrderMark;
import org.apache.commons.io.IOUtils;
import org.apache.commons.io.input.BOMInputStream;
import org.mule.api.MuleMessage;
import org.mule.api.transformer.TransformerException;
import org.mule.transformer.AbstractMessageTransformer;
public class DeleteBOM extends AbstractMessageTransformer {
#Override
public Object transformMessage(MuleMessage message, String outputEncoding)
throws TransformerException {
try (InputStream in = new BOMInputStream(IOUtils.toInputStream(message.getPayloadAsString()), ByteOrderMark.UTF_8)) {
return IOUtils.toString(in);
} catch (Exception e) {
throw new RuntimeException("Could not remove BOM marker");
}
}
}
I partially reproduced your Mule app with the following configuration:
<file:connector name="File" autoDelete="false" streaming="true" validateConnections="true" doc:name="File" />
<mulexml:dom-to-xml-transformer name="DOM_to_XML" doc:name="DOM to XML"/>
<flow name="lalaFlow">
<file:inbound-endpoint path="D:\WORK\Input" moveToDirectory="D:\WORK\Output" responseTimeout="10000" doc:name="File" fileAge="200" encoding="UTF-8"/>
<component class="org.mule.bom.DeleteBOM" doc:name="Java"/>
<transformer ref="DOM_to_XML" doc:name="Transformer Reference"/>
...
</flow>
For further reference, go to https://commons.apache.org/proper/commons-io/javadocs/api-2.2/org/apache/commons/io/input/BOMInputStream.html
You can add before splitter an Java transformer with class:
package importxmltoapis;
import org.mule.api.MuleMessage;
import org.mule.api.transformer.TransformerException;
import org.mule.transformer.AbstractMessageTransformer;
public class DeleteBOM extends AbstractMessageTransformer{
public static final String BOM = "\uFEFF";
#Override
public Object transformMessage(MuleMessage message, String outputEncoding)
throws TransformerException {
String s="";
try {s = removeBOM(message.getPayloadAsString());} catch (Exception e) {e.printStackTrace();}
return s;
}
private static String removeBOM(String s) {
if (s.startsWith(BOM)) {
s = s.substring(1);
}
return s;
}
}
Try the following
1.Use the file to string transformer instead of bytearray to string transformer .
2.Check if you big xml is read completely and if not use the file age property of the file endpoint which will enable you to read your large file completely.
my searchversion.exe file is not running in the script..why is that so?
<project name="nightly_build" default="main" basedir="checkout">
<target name="init">
<property file="initial.properties"/>
<property file="C:/Work/lastestbuild.properties"/>
<tstamp>
<format property="suffix" pattern="yyyyMMddHHmmss"/>
</tstamp>
</target>
<target name="main" depends="init">
<sequential>
<exec executable="C:/Work/Searchversion.exe"/>
...
</sequential>
</target>
</project>
Searchversion.exe will generate latestbuild.properties file. I do not have any arguments for Searchversion.exe.
Here is the code for searchversion.exe:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
namespace Search
{
class Program
{
static void Main(string[] args)
{
System.Diagnostics.Process p = new System.Diagnostics.Process();
p.StartInfo.FileName = "sslist.exe";
p.StartInfo.Arguments = "-R -H -h sinsscm01.ds.net /mobile";
p.StartInfo.UseShellExecute = false;
p.StartInfo.RedirectStandardOutput = true;
p.StartInfo.RedirectStandardError = true;
p.Start();
string procOutput = p.StandardOutput.ReadToEnd();
string procError = p.StandardError.ReadToEnd();
TextWriter outputlog = new StreamWriter("C:\\Work\\listofsnapshot.txt");
outputlog.Write(procOutput);
outputlog.Close();
string greatestVersionNumber = "";
using (StreamReader sr = new StreamReader("C:\\Work\\listofsnapshot.txt"))
{
while (sr.Peek() >= 0)
{
var line = sr.ReadLine();
var versionNumber = line.Replace(#"6.70_Extensions/6.70.102/ANT_SASE_RELEASE_", "");
if(versionNumber.Length != line.Length)
greatestVersionNumber = versionNumber;
}
}
Console.WriteLine(greatestVersionNumber);
TextWriter latest = new StreamWriter("C:\\Work\\latestbuild.properties");
latest.Write("Version_Number=" + greatestVersionNumber);
latest.Close();
}
}
}
sslist.exe gets a list of snapshots found in my version control software, and i will get the greatest version number and save it as a text (latestbuild.properties)
Two things in your script look odd.
I don't think you need the <sequential> task in the <main> target.
The depends attribute of you <main> target will cause the <init> target to run before Searchversion.exe. So, perhaps it is getting run, just too late.
Assuming #2 is the cause of your problem you should restructure your script to look like this:
<project name="nightly_build" default="main" basedir="checkout">
<target name="init">
<exec executable="C:/Work/Searchversion.exe"/>
<property file="initial.properties"/>
<property file="C:/Work/lastestbuild.properties"/>
<tstamp>
<format property="suffix" pattern="yyyyMMddHHmmss"/>
</tstamp>
</target>
<target name="main" depends="init">
...
</target>
</project>