I've got an Excel Spreadsheet in which I store all of the test Credit Cards. These credit cards have different types. Some of these are VISA, others are MasterCard, Amex etc...
I have got a test case in which I sometimes want to use VISA cards, and sometimes MasterCard cards.
Is it possible to pass parameters to the #DataProvider?
Here is my code for #DataProvider:
#DataProvider(name="dpCreditCards")
public Object[][] getCreditCards() {
Object[][] testData = null;
try {
FileInputStream fis = new FileInputStream(dir);
XSSFWorkbook workbook = new XSSFWorkbook(fis);
XSSFSheet worksheet = workbook.getSheet("Credit Cards");
String type = "";
String cardNumber = "";
int numOfRows = worksheet.getPhysicalNumberOfRows();
int j = 0;
if (numOfRows > 0) {
for (int i = 1; i < numOfRows; i++) {
XSSFRow r = worksheet.getRow(i);
if (r.getCell(0).getCellType() == Cell.CELL_TYPE_NUMERIC) {
type = Integer.toString((int)r.getCell(0).getNumericCellValue());
} else if (r.getCell(0).getCellType() == Cell.CELL_TYPE_STRING) {
type = r.getCell(0).getStringCellValue();
}
if (type.equalsIgnoreCase("visa"))
j++;
}
testData = new Object[j][1];
}
for (int i = 1; i < numOfRows; i++) {
XSSFRow r = worksheet.getRow(i);
if (r.getCell(0).getCellType() == Cell.CELL_TYPE_NUMERIC) {
type = Integer.toString((int)r.getCell(0).getNumericCellValue());
} else if (r.getCell(0).getCellType() == Cell.CELL_TYPE_STRING) {
type = r.getCell(0).getStringCellValue();
}
if (type.equalsIgnoreCase("visa")) {
if (r.getCell(1).getCellType() == Cell.CELL_TYPE_NUMERIC) {
cardNumber = Integer.toString((int)r.getCell(1).getNumericCellValue());
} else if (r.getCell(1).getCellType() == Cell.CELL_TYPE_STRING) {
cardNumber = r.getCell(1).getStringCellValue();
}
testData[i-1][0] = cardNumber;
}
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return testData;
}
I've checked this link: http://testng.org/doc/documentation-main.html#parameters-dataproviders but couldn't find anything that would work for me. It suggests to pass Method m as parameter to data provider, but I couldn't find a useful method that m has.
Thanks in advance
One way could be to read the parameters in the listeners and then set a property which can be used in the dataprovider.
Implement ITestListener or ISuiteListener, depending upon how you are structuring your tests. Set the global card property or threadlocal property (again depending upon how you are running your tests sequentially/parallely) in the onStart methods of any.
Read this property in your dataprovider.
If you just want to test a subset of your data you could filter it out in your data provider.
If you want to apply different tests to different subsets of data, then you could use different data providers for each of the test methods. Or you could use tbe Method parameter to decide what data to return from your data provider.
If you want to be able to configure the type of data to be loaded for your test at runtime, you could use a env variable/system property for this.
Bottom line:
If you run the same test against different subsets of data, you have multiple ways to specify the subset you want to check
If you want to run different tests for different subsets of data then you should probably go with multiple data providers
Related
I am trying data driven testing with two different sheets in one single excel sheet. But what I observed is same code gave two different results when I tried executing a two different test cases. It was strange. One sheet data got properly processed but for another, same code gave Null pointer exception on a particular line. Below is the code.
#DataProvider(name="testdataforinvalidvalues")
public static Object[][] readexcelretobjinvalidval() throws Exception {
System.out.println("Data provider called");
HSSFWorkbook workbook = assignworkbook();
HSSFSheet s = workbook.getSheetAt(2);
String sp = s.getSheetName();
System.out.println(sp);
HSSFRow row = s.getRow(0);
int rownum=s.getPhysicalNumberOfRows();
int colnum=row.getLastCellNum();
System.out.println(rownum);
System.out.println(colnum);
//System.out.println(rownum);
//System.out.println(colnum);
Object data[][] = new Object[rownum][colnum];
List<Object> l = new ArrayList<Object>();
for(int i=0;i<rownum-1;i++) {
row = s.getRow(i+1);
for(int j=0;j<colnum;j++) {
**HSSFCell c = row.getCell(j);**
//l.add(c.getStringCellValue());
data[i][j]=c.getStringCellValue();
}
}
return data;
The line in the code HSSFCell c = row.getCell(j); which I tried to show in bold just below for loop is throwing null pointer exception.
The test case which I tried to run is as follows.
#Test(dataProvider="testdataforinvalidvalues",dataProviderClass=Excel_Util.class)
public void testsignupdatafieldsinvval(String email, String password) {
Syncutil.Implicitwait();
System.out.println("Test case called");
try {
getdriver().get("https://www."+csvreaderutil.csvread().get(0).toString()+"/");
Marathishd marathishdpage = PageFactory.initElements(getdriver(), Marathishd.class);
Signuppagemarathishd signup = marathishdpage.letsbeginclick();
signup.emailid.sendKeys(email);
signup.password.sendKeys(password);
Syncutil.Explicitwait(signup.invalidemailerrormessage);
Syncutil.Explicitwait(signup.invalidpassworderrormessage);
Syncutil.Explicitwait(signup.enteremailmessage);
Assert.assertEquals(signup.enteremailmessage.getText(), "Enter your Email ID");
Assert.assertEquals(signup.invalidemailerrormessage.getText(), "Please enter correct Email");
Assert.assertEquals(signup.invalidpassworderrormessage.getText(), "Please enter 4 to 20 characters password without any spaces");
}catch(Exception e) {System.out.println("Exception");}
}
I am confused why the data provider code behaved differently for two different sheets.Can anyone please help me ?
I am doing a science project on my school, and I need to use several filters on my data stream. I am using MOA with filters from WEKA. The following code is part of a classifier I made so I could use the Filter with a MOA classifier. I am ware that MOA has the WEKA classifier, where I can choose filtered classifier. However I making my own, to make sure the classifier is not testing the synthetic instances.
#Override
public void trainOnInstanceImpl(Instance instnc) {
Instance aux;
Instances moaNewInstances;
weka.core.Instances mWekaInstances, mWekaNewInstances;
mWekaInstances = new weka.core.Instances("WekaInstances", mAttFastVector, windownSize);
mWekaNewInstances = new weka.core.Instances("WekaNewInstances", mAttFastVector, windownSize);
moaNewInstances = new Instances("moaNewInstances",mAttList, windownSize);
if(IsFirst)
{
getAttributes(instnc);
moaInstances = new Instances("moaInstances",mAttList, windownSize);
IsFirst= false;
}
if(cont < windownSize)
{
moaInstances.add(instnc);
cont++;
}
else
{
cont = 0;
mWekaInstances = converterToWeka.wekaInstances(moaInstances);
mFilter.setInputFormat(mWekaInstances);
mWekaNewInstances = weka.filters.Filter.useFilter(mWekaInstances, mFilter);
moaNewInstances = converterToMoa.samoaInstances(mWekaNewInstances);
moaInstances.delete();
for(int i = 0; i < moaNewInstances.size(); i++)
mLearner.trainOnInstance(moaNewInstances.get(i));
}
}
Basically the filter will be applied whenever the size of the window is reached. in the lines mFilter.setInputFormat(mWekaInstances); and mWekaNewInstances = weka.filters.Filter.useFilter(mWekaInstances, mFilter);
However those lines gives an Exception. What could be the reason?
In our project, we have different versions of excelsheets which reference each other:
C:\V1\Sample.xls //no references
C:\V2\Sample.xls //references V1
C:\V3\Sample.xls //references V2
Example of a cell value:
=MID('C:\V1\[Sample.xls]Sheet1'!$AB2;21;1)
Now I want to evaluate formulas of V3 using apache POI, I found the following example here
// Create a FormulaEvaluator to use
FormulaEvaluator mainWorkbookEvaluator = workbook.getCreationHelper().createFormulaEvaluator();
// Track the workbook references
Map<String,FormulaEvaluator> workbooks = new HashMap<String, FormulaEvaluator>();
// Add this workbook
workbooks.put("report.xlsx", mainWorkbookEvaluator);
// Add two others
workbooks.put("input.xls", WorkbookFactory.create("c:\temp\input22.xls").getCreationHelper().createFormulaEvaluator());
workbooks.put("lookups.xlsx", WorkbookFactory.create("/home/poi/data/tmp-lookups.xlsx").getCreationHelper().createFormulaEvaluator());
// Attach them
mainWorkbookEvaluator.setupReferencedWorkbooks(workbooks);
// Evaluate
mainWorkbookEvaluator.evaluateAll();
Now my problem: I do not know the locations of the files, I therefore need to get all references from the mainworkbook and then automatically (and probably recursively) add them, not static like in the example above. Is there a function to get the references or does anyone know a way to achieve this?
Additionally, I am wondering if I have to add all FormulaEvaluator to V3 or do I have to add V2 to V3 and V1 to V2 for this to work?
I currently have setIgnoreMissingWorkbooks(true) implemented, but as the values will change and we do not want to open each excel file manually to update the references I want to implement this solution. Any help is appreciated
To get all external references use following method:
private static Set<String> getReferencedWorkbooks(Workbook workbook) {
Set<String> workbookNames = new HashSet<>();
final EvaluationWorkbook evalWorkbook;
if (workbook instanceof HSSFWorkbook) {
evalWorkbook = HSSFEvaluationWorkbook.create((HSSFWorkbook) workbook);
} else if (workbook instanceof XSSFWorkbook) {
evalWorkbook = XSSFEvaluationWorkbook.create((XSSFWorkbook) workbook);
} else {
throw new IllegalStateException();
}
for (int i = 0; i < workbook.getNumberOfSheets(); i++) {
Sheet sheet = workbook.getSheetAt(i);
final EvaluationSheet evalSheet = evalWorkbook.getSheet(i);
for (Row r : sheet) {
for (Cell c : r) {
if (c.getCellType() == HSSFCell.CELL_TYPE_FORMULA) {
final EvaluationCell cell = evalSheet.getCell(c.getRowIndex(), c.getColumnIndex());
final Ptg[] formulaTokens = evalWorkbook.getFormulaTokens(cell);
for (Ptg formulaToken : formulaTokens) {
final int externalSheetIndex;
if (formulaToken instanceof Ref3DPtg) {
Ref3DPtg refToken = (Ref3DPtg) formulaToken;
externalSheetIndex = refToken.getExternSheetIndex();
} else if (formulaToken instanceof Ref3DPxg) {
Ref3DPxg refToken = (Ref3DPxg) formulaToken;
externalSheetIndex = refToken.getExternalWorkbookNumber();
} else {
externalSheetIndex = -1;
}
if (externalSheetIndex >= 0) {
final ExternalSheet externalSheet = evalWorkbook.getExternalSheet(externalSheetIndex);
workbookNames.add(externalSheet.getWorkbookName());
}
}
}
}
}
}
return workbookNames;
}
If your all of your workbooks are XLSX/XLSM you can use following code:
private static Set<String> getReferencedWorkbooksXssf(XSSFWorkbook workbook) {
Set<String> workbookNames = new HashSet<>();
final List<ExternalLinksTable> externalLinksTable = workbook.getExternalLinksTable();
for (ExternalLinksTable linksTable : externalLinksTable) {
final String linkedFileName = linksTable.getLinkedFileName();
workbookNames.add(linkedFileName);
}
return workbookNames;
}
I am in the middle of creating an app that allows users to apply for job positions and upload their CVs. I`m currently stuck on trying to make a search box for the admin to be able to search for Keywords. The app will than look through all the CVs and if it finds such keywords it will show up a list of Cvs that contain the keyword. I am fairly new to Gui design and app creation so not sure how to go about doing it. I wish to have it done via java and am using the Eclipse Window builder to help me design it. Any help will be greatly appreciated, hints, advice anything. Thank You.
Well, this not right design approach as real time search of words in all files of given folder will be slow and not sustainable in long run. Ideally you should have indexed all CV's for keywords. The search should run on index and then get the associated CV for that index ( think of indexes similar to tags). There are many options for indexing - simples DB indexing or using Apache Lucene or follow these steps to create a index using Maps and refer this index for search.
Create a map Map<String, List<File>> for keeping the association of
keywords to files
iterate through all files, and for each word in
each file, add that file to the list corresponding to that word in
your index map
here is the java code which will work for you but I would still suggest to change your design approach and use indexes.
File dir = new File("Folder for CV's");
if(dir.exists())
{
Pattern p = Pattern.compile("Java");
ArrayList<String> list = new ArrayList<String>(); // list of CV's
for(File f : dir.listFiles())
{
if(!f.isFile()) continue;
try
{
FileInputStream fis = new FileInputStream(f);
byte[] data = new byte[fis.available()];
fis.read(data);
String text = new String(data);
Matcher m = p.matcher(text);
if(m.find())
{
list.add(f.getName()); // add file to found-keyword list.
}
fis.close();
}
catch(Exception e)
{
System.out.print("\n\t Error processing file : "+f.getName());
}
}
System.out.print("\n\t List : "+list); // list of files containing keyword.
} // IF directory exists then only process.
else
{
System.out.print("\n Directory doesn't exist.");
}
Here you get the files list to show now for "Java". As I said use indexes :)
Thanks for taking your time to look into my problem.
I have actually come up with a solution of my own. It is probably very amateur like but it works for me.
JButton btnSearch = new JButton("Search");
btnSearch.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent arg0)
{
list.clear();
String s = SearchBox.getText();
int i = 0,present = 0;
int id;
try
{
Class.forName(driver).newInstance();
Connection conn = DriverManager.getConnection(url+dbName,userName,password);
Statement st = conn.createStatement();
ResultSet res = st.executeQuery("SELECT * FROM javaapp.test");
while(res.next())
{
i = 0;
present = 0;
while(i < 9)
{
String out = res.getString(search[i]);
if(out.toLowerCase().contains(s.toLowerCase()))
{
present = 1;
break;
}
i++;
}
if(tglbtnNormalshortlist.isSelected())
{
if(present == 1 && res.getInt("Shortlist") == 1)
{
id = res.getInt("Candidate");
String print = res.getString("Name");
list.addElement(print+" "+id);
}
}
else
{
if(present == 1 && res.getInt("Shortlist") == 0)
{
id = res.getInt("Candidate");
String print = res.getString("Name");
list.addElement(print+" "+id);
}
}
}
}
catch (Exception e)
{
e.printStackTrace();
}
}
});
This question already has answers here:
How to show/hide a column at runtime?
(8 answers)
Closed 1 year ago.
I have a CSV/Excel report with 5 fixed columns and I want to add more columns, depending on the input. Each report generation may require different number of columns.
The jrxml approach is done, so my question is - Can I add dynamic columns in jrxml ?
If not, what is the correct way to do it with coding ? example
Note: I prefer not to use Dynamic Jasper library
I think your purpose can be best achieved by using DynamicJasper which creates report design and layout on the fly. This will allow you to custom made report before generating it.
DynamicJasper is perfect for generating a report having dynamic number of columns.
Here is one code which I used for my N number of columns and M number of rows to create a pdf file by using JRBeanCollectionDataSource.
private List<DynaBean> convertDynaBListFrom2DAry(Object[][] ary2D, int width, int height){
logger.info("Converting report array to dynamic bean as, we have dynamic number of columns");
DynaProperty[] props = new DynaProperty[width];
for (int p=0; p < width; p++) {
DynaProperty dp = new DynaProperty("property"+p);
props[p] = dp;
}
List<DynaBean> dynaBeans = new ArrayList<>(height);
for (Object[] objects : ary2D) {
MutableDynaClass dc = new LazyDynaClass("Row", null, props);
try {
DynaBean row = dc.newInstance();
for (int c=0 ; c < width ; c++ ) {
Object obj = objects[c];
if(obj == null) {
obj = new String("");
}else if(obj.equals("null")) {
obj = new String("");
}else if(obj.equals("NaN")){
obj = new String("");
}
row.set("property"+c, obj);
}
dynaBeans.add(row);
} catch (IllegalAccessException e) {
logger.error("Exception ",e);
} catch (InstantiationException e) {
logger.error("Exception ",e);
}
}
return dynaBeans;
}